Incident review: obciążenie bazy danych, kaskadowe awarie i czego się nauczyliśmy - 27 stycznia 2026
We wtorek, 27 stycznia, doświadczyliśmy incydentu produkcyjnego, który spowodował pogorszenie wydajności w całej platformie oraz całkowity przestój u niektórych klientów enterprise z linkami do planowania o dużym wolumenie. Incydent zaczął się od podwyższonego obciążenia bazy danych, wydawał się rozwiązany, a potem ujawnił wtórne awarie w systemach downstream. Ten wpis wyjaśnia, co się stało, jak to potwierdziliśmy i co zmieniliśmy w rezultacie.

Wpływ
-
Użytkownicy o małym wolumenie doświadczyli dużych opóźnień i wolnego ładowania stron
-
Klienci enterprise z dużym obciążeniem linków do planowania doświadczyli timeoutów i przestojów
-
Później w trakcie incydentu użytkownicy z integracjami Google Calendar widzieli sporadyczne błędy
Co zauważyliśmy najpierw
O 15:30 UTC automatyczne alerty uruchomiły się z powodu podwyższonego obciążenia bazy danych. Wczesna analiza pokazała rosnącą liczbę Average Active Sessions (AAS) i szybko rosnące opóźnienie zapytań, podczas gdy ogólny ruch pozostawał w oczekiwanych granicach.

Co pokazuje ten wykres:
-
Utrzymujący się wzrost aktywnych sesji bazy danych
-
Sesje narastające zamiast szybko się kończyć
-
Silny sygnał, że zapytania stawały się wolniejsze, a nie że wzrósł ruch
To sugerowało zmianę w naszej aplikacji, a nie skok ruchu, co potwierdziła analiza ruchu.
Nasycenie CPU potwierdza wąskie gardło
Wraz ze wzrostem obciążenia rosło też użycie CPU bazy danych.


Co pokazują te wykresy:
-
Wykorzystanie CPU wyraźnie powyżej poziomu bazowego
-
Utrzymujące się nasycenie, a nie krótkie skoki
-
Wyraźna korelacja z rosnącym opóźnieniem zapytań
Na tym etapie Postgres był ograniczony przez CPU. Zapytania wykonywały się dłużej, blokowały inne i opóźnienia rozprzestrzeniały się po całym systemie.
Oś czasu (UTC)
-
15:30 – Automatyczne alerty o wysokim obciążeniu bazy danych. Wstępna diagnostyka pokazała podwyższoną aktywność
DELETEna APIv2. -
15:49 – Zaostrzyliśmy limity szybkości
DELETE, aby zmniejszyć natychmiastową presję. -
16:03 – Dalsza analiza pokazała, że ruch był normalny. Obciążenie bazy danych nadal rosło.
-
16:06 – Pierwsze zgłoszenia od klientów enterprise, którzy nie mogli załadować linków do planowania.
-
16:18 – Ogłoszono incydent. Nasycenie CPU spowodowało wzrost opóźnienia zapytań w całym systemie.
-
17:07 – Zaczęliśmy przepisywać zapytanie o dużym obciążeniu, aby zmniejszyć presję na bazę danych.
-
17:40 – Wdrożono przepisane zapytanie. Pomogło, ale nie rozwiązało problemu całkowicie.
Kluczowy punkt zwrotny
O 17:45 zidentyfikowaliśmy niezamierzoną interakcję:
Niedawna funkcja wydana w poniedziałek 26. wprowadziła wyszukiwanie rezerwacji w KBar (CMD+K). To spowodowało, że przy każdym załadowaniu strony w aplikacji webowej wykonywało się ciężkie wywołanie API.
O 17:55 zmiana KBar została cofnięta na produkcji.

Co potwierdza ten wykres:
-
Wyraźny i natychmiastowy spadek AAS po cofnięciu zmiany
-
Mniejsza presja na zapytania do bazy danych
-
Opóźnienie stabilizujące się krótko potem
To dokładnie zgadza się z czasem cofnięcia zmian i potwierdziło interakcję z KBar jako główny wyzwalacz incydentu bazy danych.
- 18:15 – Wydajność bazy danych ustabilizowała się.
W tym momencie pierwotny incydent DB został rozwiązany.
Ujawnione wtórne problemy
Po odzyskaniu bazy danych mniejsza grupa użytkowników nadal była dotknięta.
Użytkownicy z integracjami Google Calendar doświadczali błędów z powodu wyczerpania limitu Google API. Było to spowodowane zachowaniem retry u wielu konsumentów, gdy występowały błędy upstream.

Co pokazuje ten wykres:
-
Szybkie zużycie limitu w czasie okna incydentu
-
Korelacja z zachowaniem retry, a nie z nowym ruchem
-
18:40 – Zidentyfikowano przyczynę źródłową: logika retry w Atoms agresywnie odświeżająca kalendarze.
-
18:46 – Funkcjonalność Atoms została tymczasowo przerwana. Zdarzenia kalendarza zostały uzupełnione, a wykorzystanie limitu spadło.
-
18:54 – Wydajność APIv2 pozostawała lekko pogorszona; część ruchu została tymczasowo przekierowana na endpointy Vercel.
-
19:30 – APIv2 i integracje Google ustabilizowały się całkowicie.
Później zidentyfikowaliśmy dodatkowy czynnik przyczyniający się do problemu:
- Nieoczekane wywołanie promisified bez
awaitpowodowało awarie procesów Node, gdy błędy Google API wychodziły do global scope.
Przyczyna źródłowa
Główną przyczyną była nieoczekiwana interakcja między funkcjami:
-
KBar wywoływał ciężkie wywołanie API przy każdym załadowaniu strony
-
Ta ścieżka API opierała się na kosztownych zapytaniach do bazy danych; szczególnie u dużych użytkowników z wieloma bookings.
-
Nasycenie CPU zwiększyło opóźnienie zapytań w całym systemie
-
Klienci enterprise z linkami do planowania o dużym wolumenie zostali dotknięci najmocniej
Wtórne awarie (wyczerpanie limitu Google i niestabilność APIv2) nie były pierwotną przyczyną, ale zostały ujawnione, gdy system był pod obciążeniem.
Co zmieniliśmy
Od wtorku zrobiliśmy:
-
Usunęliśmy powiązanie z KBar, które wywoływało ciężkie wywołania API (#27314)
-
Wdrożyliśmy wiele optymalizacji zapytań, aby zmniejszyć obciążenie DB (#27364, #27319, #27309, #27315)
-
Zmieniliśmy paginację dla
/booking/{upcoming,…}z pre-renderowanej na on-demand, zmniejszając użycie bazy danych, podczas gdy nadal optymalizujemy endpoint (#27351) -
Naprawiliśmy asynchroniczne wywołanie bez
await, które powodowało awarie procesu Node w APIv2(#27313) -
Wprowadziliśmy różne zabezpieczenia na poziomie bazy danych, aby chronić naszą bazę w okresach ekstremalnego użycia.
-
Ograniczyliśmy wywołania do endpointów DELETE do 1 żądania na sekundę (#27359)
Zakończenie
Ten incydent nie został spowodowany przez skoki ruchu ani awarię infrastruktury. Został spowodowany nieoczekiwaną interakcją funkcji, z kaskadowymi problemami wynikającymi z zachowania retry downstream i subtelnym błędem aplikacji.
Przepraszamy za zakłócenia, zwłaszcza klientów działających na dużą skalę. Incydent z wtorku bezpośrednio wpłynął na usprawnienia tego, jak wdrażamy funkcje, chronimy naszą bazę danych i obsługujemy kaskadowe awarie.
Dzięki za cierpliwość i za trzymanie nas na wysokim poziomie.
