Costuri neașteptate pentru egress: de unde apar facturile de bandwidth
Costurile neașteptate pentru egress provin de obicei din patru obiceiuri: servirea fișierelor media din aplicație, lipsa headerelor de cache, API-uri prea vorbărețe și traficul între regiuni. Găsește sursa și redu factura fără să schimbi furnizorul.
Factura sosește și este de patru ori mai mare decât te așteptai. Linia pentru compute este aproximativ cea bugetată. Cea care nu se potrivește este cea pentru egress — octeții care ies din infrastructura ta — și există șanse reale să nu te fi gândit niciodată la asta.
Costurile neașteptate pentru egress sunt cea mai frecventă surpriză de facturare în găzduirea aplicațiilor, iar motivul este structural: nimic din procesul tău de development nu măsoară octeții. Laptopul tău nu te taxează pentru ei. Mediul de staging nu are utilizatori. Prima dată când bandwidth-ul devine vizibil este pe factură, iar până atunci ai lansat deja obiceiul care l-a generat.
Iată de unde provine în realitate, în ordinea frecvenței cu care acesta este răspunsul.
1. Servirea fișierelor media din aplicație
Acest factor le depășește cu mult pe celelalte și este aproape întotdeauna accidental.
Pui un videoclip în /public ca să demonstrezi ceva. Funcționează, așa că rămâne acolo. Acum, la fiecare accesare a paginii, containerul tău transmite acel fișier. Un videoclip de 40 MB pe o pagină cu o mie de vizitatori pe lună înseamnă 40 GB — proveniți dintr-un fișier pe care îl considerai un simplu placeholder.
Același tipar se aplică imaginilor de produs, fișierelor PDF, fișierelor încărcate de utilizatori și fonturilor. Când le adaugi, niciunul nu pare o decizie de infrastructură.
Soluția nu este una sofisticată: fișierele media statice trebuie păstrate în object storage în spatele unui CDN, nu în filesystem-ul aplicației. Aplicația ta ar trebui să servească HTML și JSON. În momentul în care transmite o imagine hero de 4 MB fiecărui vizitator, face treaba unui CDN fără niciunul dintre avantajele economice ale unui CDN.
2. Lipsa headerelor de cache
Dacă răspunsurile tale nu au headere de cache, fiecare vizitator descarcă fiecare asset la fiecare încărcare a paginii. Vizitatorii care revin descarcă totul din nou. Un crawler le descarcă de zeci de ori pe zi.
# Fingerprinted build assets never change — cache them for a year
Cache-Control: public, max-age=31536000, immutable
# HTML changes — revalidate but allow a short window
Cache-Control: public, max-age=0, must-revalidate
# Anything user-specific
Cache-Control: private, no-store
Este o modificare de o singură linie pentru fiecare clasă de răspuns și elimină în mod obișnuit cea mai mare parte a unei facturi de bandwidth, deoarece traficul eliminat este pură repetiție.
3. API-uri care returnează mai mult decât folosește clientul
Un endpoint de listare care returnează obiecte complete, deși interfața afișează trei câmpuri, trimite diferența la fiecare request, pentru totdeauna. Nu apare niciodată în profiling, deoarece este rapid — doar că este voluminos.
Verifică două lucruri pe endpoint-urile cele mai solicitate:
- Este activată compresia?
Content-Encoding: gzipsaubrpentru JSON reduce de obicei dimensiunea cu 70–80%. Este o singură linie de middleware și lipsește frecvent. - Trimiți câmpuri pe care nu le citește nimeni? Serializarea întregului rând pentru că ORM-ul a făcut acest lucru ușor este comportamentul implicit în majoritatea codebase-urilor.
Un client care face polling agravează ambele probleme cu un factor egal cu numărul de interogări pe minut.
4. Trafic între regiuni și între servicii
Dacă aplicația este într-o regiune, iar baza de date în alta, fiecare rezultat de query traversează o graniță taxată. Se poate întâmpla ușor accidental — creezi mai întâi baza de date, alegi o regiune fără să te gândești prea mult, apoi plasezi aplicația în altă parte câteva săptămâni mai târziu.
Traficul dintre propriile servicii poate fi, de asemenea, egress dacă părăsește rețeaua privată și revine printr-un hostname public. Două servicii din același workspace care comunică prin URL-urile publice plătesc de două ori pentru o conversație care nu trebuia să iasă niciodată din rețea.
În Dockup, această greșeală este greu de făcut, deoarece serviciile se adresează reciproc prin nume interne. Un serviciu ajunge la main-db.internal:5432, iar la un alt serviciu prin aliasul său <slug>.internal — traficul care rămâne în rețeaua workspace-ului nu ajunge niciodată la un listener public. Acesta este și motivul pentru care baza de date nu are implicit un hostname public: nu există nimic ce ai putea ruta accidental prin exterior.
Identifică sursa în loc să ghicești
Să ghicești care dintre cele patru cauze este responsabilă înseamnă să pierzi un ciclu de facturare. Măsoară în schimb:
Citește access log-ul după numărul de octeți, nu după numărul de request-uri. Sortează răspunsurile principale după numărul total de octeți serviți, nu după numărul de request-uri. Endpoint-ul care trimite cele mai multe date nu este, de obicei, cel apelat cel mai frecvent.
Verifică cele mai mari asset-uri statice. Dacă ceva mai mare de un megabyte este servit din aplicație, acesta este primul lucru pe care trebuie să-l muți.
# What is the service actually doing right now
dockup metrics my-project/my-api --json
# And what is it logging
dockup logs my-project/my-api -n 1000
Urmărește crawler-ele. Un bot care se comportă necorespunzător și descarcă în mod repetat fișiere mari poate reprezenta cea mai mare parte din egress-ul unei luni pe un site cu trafic uman modest. robots.txt și un noindex în mediile de preview sunt soluții ieftine.
Mediile pe care nimeni nu le ia în calcul
Două obiceiuri generează egress care nu apare niciodată în modelul mental al nimănui:
Mediile de preview. Un preview pentru fiecare pull request este cu adevărat util și îți multiplică discret amprenta. Cinci PR-uri deschise înseamnă cinci copii ale stack-ului tău, fiecare cu propriul trafic — adesea de la aceleași crawlere, deoarece URL-urile de preview sunt indexate dacă nu le oprești.
Mediile de staging cu durată lungă. Un mediu de staging care rulează de opt luni, pe care nu-l mai accesează nimeni, continuă să descarce imagini, continuă să fie accesat de crawlere și își rulează în continuare job-urile cron.
Niciuna dintre aceste situații nu este un motiv să renunți la respectivele medii. Ambele sunt însă un motiv să le limitezi: expiră preview-urile când se închide PR-ul și marchează-le cu noindex, pentru ca motoarele de căutare să nu le mai descarce în locul tău.
dockup noindex my-project/my-api --on
Cum arată o facturare bună
Ar trebui să poți răspunde la trei întrebări înainte să sosească factura:
- Ce rulează în acest moment? Inclusiv lucrurile pe care ai uitat că le-ai creat.
- Ce a consumat fiecare? Separat pentru compute și transfer, nu într-o singură cifră.
- Ce se întâmplă dacă traficul crește brusc? O limită care oprește serviciile este neplăcută. O limită care nu există este și mai rea.
Dockup măsoară separat infrastructura și planul, astfel încât taxa planului să nu ascundă utilizarea — iar creditul de 20 $ al planului Pro se aplică utilizării, nu reprezintă o reducere a taxei. Ideea este să poți vedea clar care este fiecare componentă.
Pe scurt
Mută fișierele media în object storage. Setează headere de cache. Activează compresia. Păstrează serviciile și bazele lor de date în aceeași regiune și lasă-le să comunice prin rețeaua privată, nu prin internetul public. Expiră mediile de preview și împiedică apariția lor în rezultatele de căutare.
Aceste cinci obiceiuri rezolvă aproape orice factură surprinzătoare pentru bandwidth și niciunul nu necesită să schimbi locul în care găzduiești aplicația.
Întrebări frecvente
Ce este egress-ul? Datele care ies din infrastructura ta către internet. Răspunsuri trimise utilizatorilor, fișiere descărcate, payload-uri API. Traficul inbound este de obicei gratuit; cel outbound, de regulă, nu.
De ce factura mea pentru egress este mai mare decât factura pentru compute? Aproape întotdeauna pentru că aplicația servește fișiere care ar trebui să fie pe un CDN. Un singur asset mare de pe o pagină populară poate depăși costul procesării request-urilor timp de săptămâni.
Un CDN chiar reduce costurile? Da, atunci când face cache. Origin-ul servește fișierul o singură dată pentru fiecare edge, nu o dată pentru fiecare vizitator, iar prețul CDN-ului per gigabyte este de obicei o fracțiune din cel al unei platforme de aplicații.
Costă mediile de preview la fel de mult ca producția? Costă în funcție de ceea ce consumă, iar suma este adesea mai mare decât te aștepți, deoarece fiecare mediu este o copie completă, iar URL-urile de preview sunt accesate de crawlere dacă nu împiedici acest lucru.
