Zašto Port-Share čini da svi posjetitelji web-mjesta izgledaju kao localhost
Pozadinski sustav vidi skok prosljeđivanja, a ne preglednik. Provjerite gdje se gubi izvorna adresa, pa odlučite koji joj komponent može jamčiti.
Svaki redak u dnevniku pristupa prikazuje istu loopback adresu, dok se stranica učita i certifikat se ispravno provjeri. Ništa nije pokvareno u smislu nedostupnosti i zato ovo preživljava mjesecima. Pokvarilo se pripisivanje: web pozadina bilježi adresu skoka koji je proslijedio vezu, a svaka kasnija odluka koja je vjerovala dnevniku naslijedila je isti pogrešan odgovor.
Provjere u nastavku idu od kabela prema unutra. Zaustavite se na prvoj koja objašnjava vrijednost koju vidite, jer svaki kasniji korak pretpostavlja da su prethodni već istiniti. Nijedna od njih ne zahtijeva nagađanje konfiguracije prednjeg dijela.
Slijedite dvije veze, a ne redak dnevnika
Port-Share multipleksira dva protokola na jednom TCP slušaču. OpenVPN pregledava prve bajtove dolazne veze, zadržava je kad izgleda kao njegov vlastiti protokol, a sve ostalo predaje drugom odredištu. To je odredište obično web poslužitelj na istom hostu, pa prihvaćeni socket web poslužitelja ima proces OpenVPN kao svog partnera.
ss -ltnp 'sport = :443'
ss -tnp 'dport = :8080'
Prva naredba pokazuje kome pripada javni slušač. Druga pokazuje veze koje dolaze na port pozadine, a adresa njihova partnera je ona koju će dnevnik pristupa ispisati. Ako je taj partner loopback, dnevnik je točan i informacija je izgubljena jedan sloj prije. Preimenovanje polja u dnevniku ili uključivanje modula za IP klijenta neće vratiti adresu koju veza nikada nije nosila.
Ovo je provjera koja odlučuje sve ostalo. Ako je partner pozadine adresa preglednika, dijeljenje porta nije vaš problem, nego format dnevnika.
Prosljeđivanje prometa nije ubacivanje zaglavlja
Prosljeđivač prenosi bajtove. Ne raščlanjuje HTTP pa ne može ubaciti zaglavlje u zahtjev koji nikada ne čita kao zahtjev, niti može dodati bilo što TLS toku koji propušta netaknut. Modul koji očekuje proxy zaglavlje nastavit će čekati ono koje nijedna komponenta ne proizvodi.
Originalnu adresu mogu nositi dva mehanizma i oba zahtijevaju suglasnost na obje strane. PROXY protokol dodaje malo zaglavlje na početak veze, a pozadina mora biti konfigurirana da ga očekuje; pozadina koja ga ne očekuje tretirat će te bajtove kao početak zahtjeva i neuspjeti na zbunjujuć način. Pouzdana proxy zaglavlja poput X-Forwarded-For rade kada ih postavlja proxy koji razumije HTTP i kada se pozadini kaže koji ih partneri smiju tvrditi.
Nijedno nije automatsko i nijedno nije sigurno po defaultu. Pozadina koja vjeruje svakom dolaznom proslijeđenom zaglavlju dopušta klijentu da odabere vlastitu adresu, što netočnost u dnevniku pretvara u zaobilaženje kontrole pristupa. Izvedite demonstraciju jednom na testnom hostu prije nego povjerujete bilo kojem zaglavlju na produkcijskom putu.
curl -sS -H 'X-Forwarded-For: 127.0.0.1' https://site.example.com/health
grep -F '127.0.0.1' /var/log/nginx/access.log | tail -n 3
Neobavezni direktorij mapiranja izvora
Dijeljenje porta ima neobavezni argument direktorija koji bilježi mapiranje između izvorne adrese i veze prosljeđivanja, na platformama gdje je ta funkcija implementirana. Očekuje se da web strana konzultira to mapiranje; to nije zaglavlje i ne ubacuje se u zahtjev.
Taj dizajn vrijedi znati jer objašnjava zašto neka postavljanja prijavljuju stvarne adrese a neka ne, uz naizgled identičnu konfiguraciju prednjeg dijela. Razlika je na strani primanja i obično živi u modulu ili zakrpi koju većina pakiranih web poslužitelja ne uključuje po defaultu. Pročitajte dokumentaciju svog web poslužitelja za točnu kuku koju nudi i potvrdite da je modul učitan umjesto da to pretpostavljate.
Ako krenete tim putem, tretirajte to kao integraciju s dvije polovice: mapiranje koje piše prosljeđivač i pretragu koju izvodi pozadina. Provjerite oboje i potvrdite da direktorij preživljava restart i da ne raste neograničeno na zauzetom slušaču.
Odlučite koja komponenta jamči za adresu
Prije promjene konfiguracije imenujte komponentu kojoj je dopušteno tvrditi adresu klijenta i komponente koje joj smiju vjerovati. Jedan zapisan odgovor sprječava uobičajeno odstupanje u kojem tri različita sloja vjeruju različitom izvoru.
Tri dizajna pokrivaju većinu potreba. Držite javni slušač i web slušač odvojeno, tako da web poslužitelj vidi stvarne partnere i nema problema s pripisivanjem. Postavite naprijed obrnuti proxy koji razumije HTTP, prekinite ili raščlanite zahtjev ondje i dopustite mu da postavi proslijeđeno zaglavlje za pozadinu koja vjeruje samo tom proxyju. Ili zadržite dijeljenje porta i prihvatite da dnevnici pokazuju skok, s pravilima pristupa pisanima prema identitetu aplikacije, a ne prema adresi.
Ono što ne funkcionira jest tretirati proslijeđenu loopback adresu kao dokaz da je zahtjev nastao na ovom računalu. Taj je zaključak upravo obrnut: adresa je prisutna upravo zato što je lokalna komponenta uspostavila vezu. Pravilo napisano tako propušta svakoga tko može doći do slušača.
Testirajte pravilo, ne stranicu
Stranica koja se učita dokazuje da put prosljeđivanja radi i ne govori ništa o pripisivanju. Testirajte potrošača adrese: pravilo pristupa, ograničenje brzine, zapis u reviziji, geo pretragu.
curl -sS -o /dev/null -w '%{http_code}\n' https://site.example.com/
tail -n 5 /var/log/nginx/access.log
grep -c '' /var/log/nginx/access.log
Usporedite ovlašteni vanjski zahtjev s oba zapisa, prednjim i stražnjim, i potvrdite da pravilo koje bi trebalo odbiti još uvijek odbija, a ono koje bi trebalo propustiti još uvijek propušta. Ako je redak u dnevniku točan ali se pravilo i dalje ponaša kao da su svi lokalni, pravilo čita drugo polje od onoga koje ste popravili.
Završite tako da lanac pripisivanja upišete u bilješke za postavljanje: koji slušač, koji prosljeđivač, koje zaglavlje ili mapiranje i koja je pozadina konfigurirana da mu vjeruje. Sljedećoj osobi koja pročita redak u dnevniku trebat će sva četiri, a odsutnost te bilješke razlog je zašto se isti tiket ponovno otvara godinu kasnije. Držite je uz konfiguraciju, a ne u chat niti.