Top fejl fra Cian

Top fejl fra Cian

Goddag alle! 

Mit navn er Nikita, jeg er teamleder for ingeniĂžrteamet hos Cian. En af mine opgaver i virksomheden er at reducere antallet af hĂŠndelser relateret til infrastrukturen i produktionen til nul.
Det, vi vil tale om nedenfor, har forÄrsaget os meget smerte, og formÄlet med denne artikel er at forhindre andre i at gentage vores fejl eller i hvert fald minimere deres indflydelse. 

PrĂŠambel

For lĂŠnge siden, da Cian bestod af monolitter, og der slet ikke var nogen tegn pĂ„ mikrotjenester, mĂ„lte vi tilgĂŠngeligheden af ressourcen ved at tjekke 3–5 sider. 

Hvis de svarede — alt var godt, hvis de ikke svarede i lang tid — alert. Hvor lang tid de skulle vĂŠre nede for at blive betragtet som en hĂŠndelse, blev besluttet af folk pĂ„ mĂžder. IngeniĂžrteamet deltager altid i efterforskningen af hĂŠndelsen. NĂ„r undersĂžgelsen er afsluttet, skrives en postmortem — en slags rapport pĂ„ e-mail i formatet: hvad der skete, hvor lĂŠnge det varede, hvad vi gjorde i Ăžjeblikket, hvad vi vil gĂžre i fremtiden. 

Hovedsiderne pÄ hjemmesiden eller hvordan vi ved, at vi har ramt bunden

 
For at kunne forstÄ prioriteten af fejlen, har vi fremhÊvet de mest kritiske sider for forretningsfunktionen. Ud fra dem tÊller vi antallet af succesfulde/ikke-succesfulde anmodninger og timeouts. PÄ den mÄde mÄler vi uptime. 

Lad os sige, at vi har fastslĂ„et, at der er en rĂŠkke supervigtige sektioner af hjemmesiden, der er ansvarlige for den primĂŠre service — sĂžgning og indsendelse af annoncer. Hvis antallet af anmodninger, der afsluttes med en fejl, overstiger 1%, er det en kritisk hĂŠndelse. Hvis procentdelen af fejl under primetime overstiger 0,1% i lĂžbet af 15 minutter, betragtes dette ogsĂ„ som en kritisk hĂŠndelse. Disse kriterier dĂŠkker stĂžrstedelen af hĂŠndelserne, Ăžvrige falder uden for denne artikel.

Top fejl fra Cian

Top bedste hĂŠndelser fra Cian

SÄ vi har helt sikkert lÊrt at bestemme, hvornÄr en hÊndelse er sket. 

Nu er hver hĂŠndelse detaljeret beskrevet og reflekteret i en epik i Jira. For at sige det sĂ„dan: vi har startet et separat projekt, kaldte det FAIL — her kan man kun oprette epikker. 

Hvis vi samler alle fejlene fra de seneste Är, er de dominerende: 

  • hĂŠndelser relateret til mssql;
  • hĂŠndelser forĂ„rsaget af eksterne faktorer;
  • administratorfejl.

Lad os se nÊrmere pÄ administratorfejl samt nogle andre interessante fiaskoer.

Femte plads — "Vi organiserer DNS"

Det var en grÄ tirsdag. Vi besluttede at organisere DNS-klyngen. 

Vi Þnskede at migrere interne dns-servere fra bind til powerdns, ved at dedikere fuldstÊndig separate servere, hvor der ikke er andet end dns. 

Vi placerede en dns-server i hver af vores datacenters lokationer, og nu var tiden kommet til at migrere zoner fra bind til powerdns og skifte infrastrukturen til de nye servere. 

I den mest hektiske periode af migreringen var der kun én tilbage servere, som var angivet i de lokale cache-bind pÄ alle servere, og den var i datacentret i Sankt Petersborg. Dette datacenter var oprindeligt blevet deklareret som ikke-kritisk for os, men blev pludselig et single point of failure.
Lige i denne migrationsperiode gik forbindelsen mellem Moskva og Sankt Petersborg ned. Vi var faktisk uden DNS i fem minutter og kom op igen, da hoster fejlen blev rettet. 

Konklusioner:

Tidligere havde vi overset eksterne faktorer under forberedelserne til arbejdet, men nu medtager vi dem ogsÄ pÄ listen over, hvad vi forbereder os pÄ. Og nu strÊber vi efter, at alle komponenter er reserveret til n-2, og at vi under arbejdet kan sÊnke dette niveau til n-1.

  • NĂ„r du laver handlingsplanen, skal du notere punkter, hvor tjenesten kan falde, og tĂŠnke pĂ„ scenarier, hvor alt gĂ„r "vĂŠrre end vĂŠrst", pĂ„ forhĂ„nd.
  • Fordel interne dns-servere pĂ„ forskellige geolokationer/datacentre/rack/switches/indgange.
  • Installer en lokal cache dns-server pĂ„ hver server, som omdirigerer forespĂžrgsler til de primĂŠre dns-servere, og i tilfĂŠlde af utilgĂŠngelighed vil svare fra cachen. 

Fjerde plads — "Vi organiserer Nginx"

En skĂžn dag besluttede vores team, at "nu er det nok", og processen med at refaktorere nginx-konfigurationerne blev ivĂŠrksat. HovedmĂ„let er at give konfigurationerne en intuitiv struktur. Tidligere var alt "historisk opstĂ„et" og havde ingen logik i sig. Nu har vi flyttet hver server_name til en tilsvarende fil og kategoriseret alle konfigurationer i mapper. For at sige det mildt — konfigurationen indeholder 253949 linjer eller 7836520 tegn og fylder nĂŠsten 7 megabyte. Øverste niveau af strukturen: 

Nginx-struktur

├── adgang
│   ├── allow.list
...
│   └── whitelist.conf
├── geobase
│   ├── exclude.conf
...
│   └── geo_ip_to_region_id.conf
├── geodb
│   ├── GeoIP.dat
│   ├── GeoIP2-Country.mmdb
│   └── GeoLiteCity.dat
├── inc
│   ├── error.inc
...
│   └── proxy.inc
├── lists.d
│   ├── bot.conf
...
│   ├── dynamic
│   └── geo.conf
├── lua
│   ├── cookie.lua
│   ├── log
│   │   └── log.lua
│   ├── logics
│   │   ├── include.lua
│   │   ├── ...
│   │   └── utils.lua
│   └── prom
│       ├── stats.lua
│       └── stats_prometheus.lua
├── map.d
│   ├── access.conf
│   ├── ..  
│   └── zones.conf
├── nginx.conf
├── robots.txt
├── server.d
│   ├── cian.ru
│   │   ├── cian.ru.conf
│   │   ├── ...
│   │   └── my.cian.ru.conf
├── service.d
│   ├── ...
│   └── status.conf
└── upstream.d
    ├── cian-mcs.conf
    ├── ...
    └── wafserver.conf

Det blev markant bedre, men under omdĂžbning og fordeling af konfigurationer havde nogle af dem forkerte filendelser og kom ikke ind i direktivet include *.conf. Som fĂžlge heraf blev nogle hosts utilgĂŠngelige og returnerede 301 til forsiden. Fordi svarkoden ikke var 5xx/4xx, blev det ikke opdaget med det samme, men fĂžrst tidligt om morgenen. Derefter begyndte vi at skrive tests til kontrol af infrastrukturkomponenterne.

Konklusioner: 

  • Strukturer konfigurationerne korrekt (ikke kun nginx) og overvej strukturen tidligt i projektet. Det vil gĂžre dem mere forstĂ„elige for teamet, hvilket i sin tur vil reducere TTM.
  • Skriv tests for nogle infrastrukturkomponenter. For eksempel: kontrol, at alle nĂžgle server_name returnerer den korrekte status, + svarindholdet. Det er tilstrĂŠkkeligt at have bare et par scripts, der kontrollerer de grundlĂŠggende funktioner af komponenten, sĂ„ man ikke nervĂžst skal huske, hvad man ellers skal tjekke klokken 3 om natten. 

Tredje plads — "Pludselig var der ikke mere plads i Cassandra"

Dataene voksede stÞt, og alt var fint, indtil klustret Cassandra begyndte at fejle ved reparation af store keyspaces, fordi det ikke kunne gennemfÞre compaction. 

PĂ„ en dyster dag nĂŠsten forvandlede klustret sig til et grĂŠskar, nemlig:

  • der var ca. 20% plads tilbage i hele klustret;
  • det var ikke muligt at tilfĂžje noder ordentligt, fordi cleanup ikke kunne gennemfĂžres efter tilfĂžjelsen af en node pĂ„ grund af pladsmangel pĂ„ partitionerne;
  • ydelsen falder lidt, fordi compaction ikke virker; 
  • klustret kĂžrer i nĂždtilstand.

Top fejl fra Cian

Udgangen — vi har tilfþjet fem ekstra noder uden cleanup, hvorefter vi begyndte systematisk at fjerne dem fra klyngen og genindsétte dem som tomme noder, hvor der ikke var plads tilbage. Tiden brugt hertil har véret betydeligt mere, end vi þnskede. Der var en risiko for delvis eller total utilgéngelighed af klyngen. 

Konklusioner:

  • PĂ„ alle servere mĂ„ cassandra ikke have mere end 60% af pladsen optaget i hver partition. 
  • De mĂ„ ikke vĂŠre mere end 50% belastet pĂ„ CPU.
  • Man bĂžr ikke overse kapacitetsplanlĂŠgning, og det skal overvejes for hver komponent ud fra dens specifikation.
  • Jo flere noder i klyngen, desto bedre. Servere med smĂ„ datamĂŠngder genopretter hurtigere, og en sĂ„dan klynge er lettere at genoplive. 

Andet sted — «Data forsvandt fra consul key-value storage»

Til service discovery bruger vi, ligesom mange, consul. Men vi bruger ogsÄ dens key-value til blue-green deployment af monoliten. Her opbevares oplysninger om aktive og inaktive upstreams, som udskiftes under deployment. Der blev skrevet en deploy-service, som interagerede med KV. PÄ et tidspunkt forsvandt dataene fra KV. Vi genskabte det fra hukommelsen, men med en rÊkke fejl. Som fÞlge heraf blev belastningen pÄ upstreams ikke fordelt jÊvnt under deployment, og vi fik mange 502-fejl pÄ grund af overbelastning af backendene pÄ CPU. I sidste ende flyttede vi fra consul KV til postgres, hvorfra det ikke er sÄ nemt at slette dem.  

Konklusioner:

  • Tjenester uden nogen form for autentifikation mĂ„ ikke indeholde kritiske data, der er nĂždvendige for webstedets funktion. For eksempel, hvis du ikke har autentifikation i ES — er det bedst at forhindre adgang pĂ„ netvĂŠrksniveau fra alle steder, hvor det ikke er nĂždvendigt, kun lade de nĂždvendige vĂŠre, samt at gĂžre action.destructive_requires_name: true.
  • Arbejd med mekanismen for backup og genopretning pĂ„ forhĂ„nd. For eksempel, lav et script (for eksempel pĂ„ python), der kan bĂ„de tage backup og genoprette.

FĂžrste sted — «Kaptajn Ă„benbarhed» 

PĂ„ et tidspunkt bemĂŠrkede vi en ujĂŠvn fordeling af belastningen pĂ„ nginx upstreams, nĂ„r der var 10+ servere i backend. Da round-robin dirigerede anmodninger fra den fĂžrste til den sidste upstream i rĂŠkkefĂžlge, og hver genstart af nginx startede forfra, fik de fĂžrste upstreams altid flere anmodninger end de andre. Som fĂžlge heraf arbejdede de langsommere, hvilket pĂ„virkede hele hjemmesiden. Dette blev stadig mere tydeligt i takt med, at trafikmĂŠngden steg. At opdatere nginx for at inkludere random lĂžste ikke problemet — vi skulle genarbejde en masse lua-kode, der ikke fungerede pĂ„ version 1.15 (pĂ„ det tidspunkt). Vi endte med at patch vores nginx 1.14.2 og indfĂžre understĂžttelse af random. Dette lĂžste problemet. Denne fejl vinder prisen for 'kaptejn uvidenhed'.

Konklusioner:

Det var meget interessant og spÊndende at undersÞge denne fejl). 

  • Organiser overvĂ„gningen, sĂ„ den hurtigt hjĂŠlper med at finde sĂ„danne flingeringer. For eksempel kan man bruge ELK til at overvĂ„ge rps pĂ„ hver backend af hver upstream og fĂžlge deres svartider set fra nginx. I dette tilfĂŠlde hjalp det os med at identificere problemet. 

De fleste fejl kunne vÊre undgÄet med en mere omhyggelig tilgang til det, man laver. Man skal altid huske pÄ Murphys lov: Anything that can go wrong will go wrong, og bygge komponenterne med det i mente. 

Kilde: habr.com

KĂžb pĂ„lidelig webhosting med DDoS-beskyttelse, VPS VDS-servere đŸ”„ KĂžb pĂ„lidelig webhosting med DDoS-beskyttelse, VPS VDS-servere | ProHoster