Sobes.tech
Middle+

Opowiedz o ostatnim błędzie — co się stało, jak go znaleźli i jak rozwiązali?

sobes.tech AI

Odpowiedź od AI

W jednym z naszych ostatnich projektów w Go napotkaliśmy problem wycieku pamięci w serwisie obsługującym dużą liczbę równoległych żądań. System zaczął stopniowo zwalniać i ostatecznie zawiesił się z błędem out-of-memory.

Przyczyną był niewłaściwy sposób korzystania z gorutyn: uruchamialiśmy gorutynę dla każdego żądania, ale nie kontrolowaliśmy ich kończenia ani nie zwalnialiśmy zasobów związanych z kontekstem.

Problem został wykryty za pomocą profilera pprof, który pokazał wzrost liczby gorutyn i zużycia pamięci.

Rozwiązanie:

  • Dodaliśmy kontekst z limitem czasu i anulowaniem dla gorutyn.
  • Przepisałem obsługę żądań, aby zagwarantować zakończenie gorutyn.
  • Wdrożyliśmy pulę gorutyn, aby ograniczyć maksymalną liczbę jednocześnie działających gorutyn.

Przykład użycia kontekstu do anulowania gorutyny:

ctx, cancel := context.WithTimeout(context.Background(), time.Second*5)
defer cancel()
go func(ctx context.Context) {
    select {
    case <-ctx.Done():
        // czyszczenie i zakończenie
        return
    // obsługa
    }
}(ctx)