Terminalen ansluter, prompten visas och alla är överens om att SSH-åtkomsten fungerar. Sedan når en databasklient på laptopen fortfarande inte den privata värden, och sessionen får skulden. Det som byggdes var ett skal, och det är ett av fyra ganska olika gränssnitt som SSH kan erbjuda. Namnge gränssnittet först och testa sedan att applikationen verkligen använder det. Ordningen spelar roll, eftersom varje gränssnitt misslyckas på sitt eget sätt.

Namnge gränssnittet innan du jämför något

handboken för OpenSSH-klienten skiljer mellan fyra mekanismer som är lätta att blanda ihop. Ett skal eller ett fjärrkommando körs på SSH-värden. En lokal vidarebefordran öppnar en lyssnande socket på klienten och gör den vidare anslutningen från den fjärran sidan. En fjärrvidaresbefordran gör det motsatta och lyssnar på serversidan. Dynamisk vidarebefordran exponerar en SOCKS-slutpunkt för program som vet hur man använder den.

  • Skal: programmet körs på den fjärran maskinen, ingenting lyssnar lokalt.
  • Lokal vidarebefordran: din laptop har en port, den fjärran värden gör den utgående anslutningen.
  • Fjärrvidaresbefordran: den fjärran sidan har en port, trafiken kommer tillbaka mot dig.
  • Dynamisk: en SOCKS-proxy på klienten, används bara av proxy-medvetna applikationer.

Ingen av dessa installerar en rutt. Ett program som ignorerar proxyinställningar, eller talar UDP, eller slår upp namn själv, påverkas inte av en aktiv SSH-session. Det är inte en bugg i SSH; det är omfattningen av det gränssnitt du valde.

Lokala, fjärran och dynamiska vidarebefordringar skiljer sig i vem som lyssnar

Den skillnad som avgör de flesta fall är vem som äger den lyssnande socketen. Med en lokal vidarebefordran lyssnar klienten och den fjärran änden ringer destinationen, och därför slås destinationsadressen upp från serverns synvinkel. Med en fjärrvidaresbefordran lyssnar servern och anslutningen bärs tillbaka till din sida, och så exponerar du en lokal tjänst utan att publicera den direkt.

ssh -N -L 5432:db.internal.example:5432 [email protected]
ssh -N -D 1080 [email protected]
ss -ltnp | grep -E '5432|1080'

Det första kommandot binder port 5432 på laptopen och vidarebefordrar den till databasen så som den ses från bastionen. Det andra skapar en SOCKS-proxy på port 1080. Det tredje kommandot bekräftar vilka processer som faktiskt lyssnar, och det är det enda beviset på att vidarebefordran finns i stället för att ha misslyckats tyst på en portkonflikt.

Dynamisk vidarebefordran förtjänar sin egen varning: den täcker bara applikationer som respekterar SOCKS. En webbläsare kan riktas mot den, ett kommandoradsverktyg kan få veta att det ska använda den, och en databasdrivrutin med sin egen anslutningsstack kan vanligtvis inte. Att anta att varje program på maskinen nu använder tunneln är det vanligaste misstaget i hela detta område.

Tunnel-enhetsläget är det enda riktiga nätverksundantaget

OpenSSH stöder också -w tunnel-enhetsvidarebefordran, som skickar ett punkt-till-punkt-gränssnitt i stället för en TCP-lyssnare. Det är en äkta nätverkstunnel, och den konfigureras medvetet, inte som en bieffekt av att öppna ett skal.

sudo ssh -w 0:0 [email protected]
ip addr show tun0

Den behöver motsvarande gränssnittsnummer tillgängliga i båda ändar, rätt konfiguration på servern och tillräckliga rättigheter på klienten för att skapa enheten. Den behöver också en adresserings- och routingplan, eftersom ett bart gränssnitt inte bär någon policy om vilka destinationer som ska använda det.

Ändå slutar tunneln vid den fjärran värden. Det skydd SSH-transporten gav slutar där, och den vidare anslutningen är ett separat hopp. En VPN-gateway har samma form av gräns, och därför bör jämförelsen handla om omfattning och avslut snarare än om vilket verktyg som är starkast. Att namnge den gränsen högt avgör också diskussionen om en tunnel «krypterar allt», för det gör den uppenbarligen inte.

Testa att din applikation använder det gränssnitt du byggde

Verifieringen är per applikation, inte per session. En fungerande vidarebefordran bevisar att porten är bunden och att den fjärran sidan kan ringa; den bevisar inte att programmet du bryr dig om anslöt genom den.

curl -sS --socks5-hostname 127.0.0.1:1080 -o /dev/null -w '%{http_code}\n' https://app.internal.example/health
psql "host=127.0.0.1 port=5432 dbname=app sslmode=require" -c 'select 1'

Det första kommandot skickar en begäran genom SOCKS-slutpunkten med värdnamnet uppslaget på distans, och det andra prövar den vidarebefordrade databasporten med TLS fortfarande krävt. Kör samma tester med vidarebefordran stoppad för att bekräfta att de misslyckas, eftersom ett test som passerar båda vägarna aldrig använde tunneln.

Jämför sedan med ett routat VPN bara i de dimensioner som spelar roll: vilka destinationer som täcks, vilka protokoll som fungerar, var skyddet slutar och vem som måste godkänna åtkomsten. En vidarebefordran för en enda tjänst kan vara det smalare och bättre svaret, medan ett VPN är rätt form när många applikationer behöver samma nätverksväg. Ingen av dem ger allt som nås från dess fjärra slutpunkt.

Relaterade artiklar