2012-11-05 25 views
50
1 S postgres 5038 876 0 80 0 - 11962 sk_wai 09:57 ?  00:00:00 postgres: postgres my_app ::1(45035) idle                     
1 S postgres 9796 876 0 80 0 - 11964 sk_wai 11:01 ?  00:00:00 postgres: postgres my_app ::1(43084) idle    

Widzę ich wiele. Próbujemy naprawić nasz wyciek połączenia. Ale tymczasem chcemy ustawić limit czasu dla tych bezczynnych połączeń, może maksymalnie do 5 minut.Czy istnieje limit czasu dla wolnych połączeń PostgreSQL?

+0

jak są łączysz się z DB? socketTimeout może być tym, czego szukasz. – Doon

+0

Mamy starą aplikację internetową Pylons i użyliśmy SQLAlchemy, ale najwyraźniej nie używaliśmy jej poprawnie. Nie pamiętam. Próbujemy naprawić wyciek. 'socketTimeout' z dokumentu wygląda tak, jak zamknięcie połączenia z bazą danych. Próbuję zamknąć każdy bezczynny, a licznik rozpoczyna się natychmiast po ustanowieniu połączenia. – user1012451

+4

patrz http://stackoverflow.com/questions/12391174/is-it-possible-to-configure-postgresql-to-automatically-close-idle-connections – Doon

Odpowiedz

69

Wygląda na to, że w aplikacji jest wyciek połączenia, ponieważ nie może zamknąć połączonych połączeń. Nie masz problemów tylko z sesjami <idle> in transaction, ale ze zbyt dużą liczbą połączeń.

Zabijanie połączeń nie jest właściwą odpowiedzią, ale jest to tymczasowe obejście problemu.

Zamiast ponownie uruchamiać PostgreSQL, aby uruchomić wszystkie inne połączenia z bazy danych PostgreSQL, zobacz: How do I detach all other users from a postgres database? i How to drop a PostgreSQL database if there are active connections to it?. Ta ostatnia pokazuje lepsze zapytanie.

Aby ustawić limity czasu, jak @Doon zasugerował, zobacz How to close idle connections in PostgreSQL automatically?, który zaleca użycie PgBouncer do proxy dla PostgreSQL i zarządzanie bezczynnymi połączeniami. Jest to bardzo dobry pomysł, jeśli masz wadliwą aplikację, która i tak przecieka połączenia; I bardzo mocno polecam konfigurację PgBouncer.

Nie wykona tutaj żadnej pracy, ponieważ aplikacja jest nadal podłączona i jest żywa, po prostu nie powinna być.

W PostgreSQL 9.2 i wyżej, można użyć nowej kolumny state_change datownika i pole pg_stat_activitystatus wdrożyć żniwiarka bezczynności połączenia. Mieć pracę cron uruchomić coś takiego:

SELECT pg_terminate_backend(pid) 
    FROM pg_stat_activity 
    WHERE datname = 'regress' 
     AND pid <> pg_backend_pid() 
     AND state = 'idle' 
     AND state_change < current_timestamp - INTERVAL '5' MINUTE; 

w starszych wersjach należy wdrożyć skomplikowane systemy, które śledzą gdy połączenie poszedł bezczynny. Nie zawracaj sobie głowy; po prostu użyj pgbouncer.

+0

Dobrze, ale zabije inne backendi PgAdmin. Użyj dodatkowego warunku nazwa_aplikacji = '' –

+0

Czy mogę uruchomić pg_terminate_backend, jeśli używam pgbouncer? –

+0

@HenleyChiu Nie rozumiem, dlaczego nie, chociaż nie sprawdziłem konkretnie. –

15

W PostgreSQL 9.1, bezczynne połączenia z następującym zapytaniem. Pomogło mi to odeprzeć sytuację, która uzasadniała ponowne uruchomienie bazy danych. Zdarza się to głównie w przypadku otwartych i niepoprawnie zamkniętych połączeń JDBC.

SELECT 
    pg_terminate_backend(procpid) 
FROM 
    pg_stat_activity 
WHERE 
    current_query = '<IDLE>' 
AND 
    now() - query_start > '00:10:00'; 
+0

pg_terminate_backend znajduje się od 8,4 –

+0

Uratowałem moje życie !! –

20

W PostgreSQL 9.6, jest to nowa opcja, która powinna osiągnąć idle_in_transaction_session_timeout co opisujesz. Można ustawić go za pomocą komendy SET, np:

SET SESSION idle_in_transaction_session_timeout = '5min'; 
+0

To jest niedorzeczne, że muszę zapytać o coś tak prostego, ale jestem zupełnie nowy dla baz danych - Czy mógłby Pan podać bardzo prosty przykład wykorzystania tej funkcji? –

+2

Nie ma problemu, zaktualizowałem odpowiedź. – shosti

+0

Coś takiego w poprzednich wersjach PostgreSQL ?? – sdsc81

0

jeśli używasz postgresql 9.6+, następnie w postgresql.conf można ustawić

idle_in_transaction_session_timeout = 30000(ms)

Powiązane problemy