هل هناك مهلة لاتصالات PostgreSQL الخاملة؟




database-connection (3)

إذا كنت تستخدم postgresql 9.6+ ، في postgresql.conf الخاص بك يمكنك تعيين

idle_in_transaction_session_timeout = 30000 (ميلي ثانية)

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             

أرى الكثير منهم. نحن نحاول إصلاح تسرب الاتصال لدينا. ولكن في الوقت نفسه ، نريد تعيين مهلة لهذه الاتصالات البعيدة ، ربما تصل إلى 5 دقائق كحد أقصى.


في PostgreSQL 9.1 ، اتصالات الخمول مع الاستعلام التالي. لقد ساعدني على تجنب الوضع الذي يبرر إعادة تشغيل قاعدة البيانات. يحدث هذا غالبًا مع اتصالات JDBC المفتوحة وغير مغلقة بشكل صحيح.

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

يبدو أن لديك تسرب اتصال في التطبيق الخاص بك لأنه فشل لإغلاق الاتصالات المجمّعة . لا تواجه مشكلات مع <idle> in transaction جلسات <idle> in transaction ، ولكن مع وجود عدد كبير جدًا من الاتصالات بشكل عام.

اتصالات Killing ليست الإجابة الصحيحة لذلك ، ولكنها حل مؤقت مؤقت.

بدلاً من إعادة تشغيل PostgreSQL لتشغيل جميع الاتصالات الأخرى خارج قاعدة بيانات PostgreSQL ، انظر: كيف يمكنني فصل جميع المستخدمين الآخرين من قاعدة بيانات postgres؟ وكيفية إسقاط قاعدة بيانات PostgreSQL إذا كانت هناك اتصالات نشطة لها؟ . هذا الأخير يظهر استعلام أفضل.

لتحديد المهلات ، كما اقترحDoon انظر كيف تغلق اتصالات الخمول في PostgreSQL تلقائيا؟ ، والتي تنصحك باستخدام PgBouncer إلى الوكيل لـ PostgreSQL وإدارة اتصالات الخمول. هذه فكرة جيدة جداً إذا كان لديك تطبيق buggy الذي تسرب اتصالات على أي حال؛ أوصي بشدة بتكوين PgBouncer.

لن تقوم خدمة Keepalive لبرنامج التعاون الفني بتنفيذ المهمة هنا ، لأن التطبيق لا يزال متصلاً وعلى قيد الحياة ، لا ينبغي أن يكون كذلك.

في PostgreSQL 9.2 وما state_change ، يمكنك استخدام عمود timestamp state_change الجديد state_change status الخاص بـ pg_stat_activity لتطبيق pg_stat_activity اتصال pg_stat_activity . لديك مهمة كرون تشغيل شيء من هذا القبيل:

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;

في الإصدارات الأقدم تحتاج إلى تنفيذ أنظمة معقدة تتبع عندما يكون الاتصال خاملاً. لا تهتم مجرد استخدام pgbouncer.





database-connection