تصویر کلی
Standby میتواند WAL را از Archive، pg_wal و Streaming دریافت و بازپخش کند؛ standby.signal نقطه ورود به این حالت است.
برای فهم این موضوع بهتر است اجزا را بهعنوان یک مسیر ببینیم، نه مجموعهای از گزینههای مستقل. در Production معمولاً مشکل زمانی شکل میگیرد که تنظیم روی دیسک، وضعیت Runtime و فرض تیم درباره رفتار سیستم با هم یکی نیستند. به همین دلیل مشاهده وضعیت مؤثر، Log و Metric باید کنار Configuration بررسی شود.
اجزای اصلی و مرز مسئولیت
Streaming Replication بهصورت پیشفرض asynchronous است و برای جلوگیری از حذف زودهنگام WAL میتوان از Archive، wal_keep_size یا Replication Slot استفاده کرد.
در طراحی عملی، برای هر جزء یک سؤال روشن بنویسید: چه ورودی میگیرد، چه خروجی تولید میکند، چه Stateای نگه میدارد و در خرابی چه کسی مسئول Recovery است. این مدل ساده کمک میکند خطاهای شبکه، هویت، ذخیرهسازی یا Replication بهاشتباه به جزء دیگری نسبت داده نشوند.
خطاهای رایج
Synchronous replication میتواند دوام بیشتری بدهد اما latency و contention را بالا ببرد؛ Failover بدون طراحی Timeline و بازاتصال Standbyها کامل نیست.
خطای دیگر، فعالکردن قابلیت پیشرفته بدون تعریف معیار موفقیت است. قبل از تغییر، Baseline بگیرید؛ بعد از تغییر همان Signalها را مقایسه کنید. اگر سیستم توزیعشده است، Failure Modeهای قطع شبکه، Restart، Lag، Timeout و از دسترفتن Dependency را نیز آزمایش کنید.
چکلیست عملی
- نسخه و Configuration مؤثر را ثبت کنید، نه فقط فایل مورد انتظار را.
- مسیر داده و کنترل را جدا رسم کنید.
- Health، Latency، Error Rate و ظرفیت را قبل و بعد از تغییر مقایسه کنید.
- برای تغییرات Stateful، Backup/Restore یا Rollback واقعی را آزمایش کنید.
- دسترسی مدیریتی را حداقل کنید و Log تصمیمها را نگه دارید.
- مستندات همان نسخه محصول را مرجع نهایی قرار دهید.
تمرین IROSG
یک محیط کوچک آزمایشی بسازید و فقط یک Failure را تزریق کنید؛ مثلاً قطع Upstream، حذف یک Replica، خطای DNS یا تغییر Route. قبل از آزمایش بنویسید انتظار دارید کدام Metric و Log تغییر کند. بعد نتیجه واقعی را با انتظار مقایسه کنید. این تمرین معمولاً سریعتر از حفظکردن Optionها، مدل ذهنی سیستم را اصلاح میکند.
مرجع
این راهنما بر پایه مستندات رسمی PostgreSQL نوشته شده و مثالهای عملی تحریریه برای آموزش دفاعی و عملیاتی هستند.
WAL را به عنوان جریان تغییر بفهمیم
PostgreSQL تغییرهای لازم برای بازیابی را در گزارش پیشنگار ثبت میکند. در تکثیر فیزیکی، standby این جریان را دریافت و بازپخش میکند تا به وضعیت سازگار نزدیک شود. دریافت بایت و اعمال تغییر دو مرحلهاند. ممکن است شبکه سریع باشد و داده دریافت شود، اما بازپخش به دلیل فشار دیسک یا کارهای دیگر عقب بماند. بنابراین عبارت کلی «تکثیر تأخیر دارد» باید به پرسش دقیقتر تبدیل شود: فاصله در ارسال است، دریافت است، نوشتن پایدار است یا بازپخش؟ هرکدام مسیر بررسی متفاوتی دارد.
برای یک سامانه سفارش، تراکنشی آزمایشی با شناسه مشخص روی primary ثبت کنید و زمان قابل مشاهده شدن آن روی standby را اندازه بگیرید. همزمان وضعیت فرایندهای تکثیر و منابع میزبان را ثبت کنید. اگر فقط زمان اتصال شبکه را اندازه بگیرید، فاصله دید کاربر از داده تازه را نمیسنجید. برای گزارشهای حساس به تازگی، همین فاصله کاربردی اهمیت دارد. در مستند سرویس روشن کنید آیا خواندن از standby میتواند داده کمی قدیمی برگرداند و برنامه در برابر این وضعیت چه انتظاری دارد.
ایجاد پایه سازگار پیش از دنبال کردن جریان
یک standby تازه به نقطه شروع سازگار نیاز دارد؛ کپی دلخواه فایلهای یک پایگاه داده فعال جای روش پشتیبان پایه معتبر را نمیگیرد. روش ایجاد پایه باید با مستندات نسخه نصبشده هماهنگ باشد و WAL لازم برای ادامه بازیابی در دسترس بماند. در آزمایش، زمان شروع کپی، پایان آن و اولین اتصال جریان را ثبت کنید. اگر کپی طولانی است، فاصله ایجادشده ممکن است به حجم قابل توجهی WAL نیاز داشته باشد. ظرفیت و نگهداری این فاصله باید پیش از شروع سنجیده شود.
اعتبار اتصال تکثیر نیز باید محدود باشد. حسابی که فقط برای دریافت جریان لازم است نباید به طور پیشفرض حساب روزمره مدیر پایگاه داده باشد. مسیر شبکه، قواعد اتصال و رمزنگاری انتقال را با نیاز محیط تطبیق دهید. در گزارش عیبیابی، خطای احراز هویت را از نبود مسیر شبکه جدا کنید. تلاش مکرر با اعتبار اشتباه ممکن است گزارشها را پر کند اما با افزایش زمان انتظار یا فضای دیسک حل نمیشود. مشاهده پیام دقیق سمت ارسال و دریافت، راه تشخیص را کوتاهتر میکند.
slot حفاظت میکند، اما هزینه نگهداری دارد
Replication slot میتواند مانع کنار گذاشته شدن WAL مورد نیاز مصرفکننده شود. این ویژگی برای جلوگیری از شکاف مفید است، ولی مصرفکننده متوقفشده ممکن است باعث باقی ماندن داده زیادی شود. بنابراین ساخت slot پایان کار نیست؛ مالک، هدف و معیار هشدار آن باید ثبت شود. slot مربوط به standby حذفشده اگر فراموش شود، میتواند مشکل ظرفیت ایجاد کند. از طرف دیگر، حذف عجولانه slot فعال ممکن است نیاز به ایجاد پایه تازه را به همراه داشته باشد. تصمیم باید بر اساس وضعیت واقعی مصرفکننده باشد.
در تمرین، standby آزمایشی را برای مدتی متوقف کنید و رشد WAL نگهداریشده را ببینید. سپس آن را برگردانید و زمان رسیدن به وضعیت نزدیک را اندازه بگیرید. نرخ تولید WAL در ساعات شلوغ میتواند با ساعات آرام متفاوت باشد؛ ظرفیت بر اساس یک نمونه کوتاه خوشبینانه انتخاب نشود. محدودیتهای قابل تنظیم و رفتار پس از عبور از آنها را در مستندات همان نسخه بررسی کنید. هدف، داشتن هشدار پیش از پر شدن دیسک primary است، نه کشف مشکل بعد از توقف تمام نوشتنهای برنامه.
ناهمگام و همگام دو قرارداد متفاوتاند
در تکثیر ناهمگام، تأیید تراکنش روی primary الزاماً به معنی رسیدن آن به standby نیست. اگر primary در فاصله انتقال از دست برود، تصمیم ارتقا میتواند با از دست رفتن بخشی از تراکنشهای تازه همراه باشد. این فاصله باید در هدف بازیابی داده دیده شود. تکثیر همگام میتواند قرارداد تأیید را تغییر دهد، اما پاسخ دقیق به تنظیم انتظار و مقصدهای لازم وابسته است. بهتر است تیم به جای استفاده کلی از واژه «بدون از دست رفتن داده»، مرحلهای را که تأیید به آن وابسته است صریح بیان کند.
انتظار برای مقصد همگام میتواند زمان تراکنش را به شبکه و سلامت standby وابسته کند. در آزمایش، تأخیر مسیر را افزایش دهید و زمان ثبت سفارش را ببینید. سپس قطع مقصد را بررسی کنید و رفتار مورد انتظار را با سیاست دسترسپذیری مقایسه کنید. این انتخاب یک مبادله عملی میان دوام و ادامه پذیرش نوشتن است. هیچ تنظیمی بدون شناخت نیاز کسبوکار بهترین گزینه همه سامانهها نیست. نتیجه تصمیم باید به زبان قابل فهم برای مالک سرویس نیز بیان شود، نه فقط به صورت نام پارامتر.
خواندن از standby و تعارض با بازیابی
Standby میتواند برای خواندن مفید باشد، اما اجرای پرسوجوهای طولانی ممکن است با نیاز بازپخش تغییرها برخورد کند. رفتار دقیق به تنظیمات و نوع تعارض وابسته است. برای سامانه گزارش، یک پرسوجوی نماینده را هنگام بار نوشتن اجرا کنید و خطاها، زمان اجرا و فاصله بازپخش را ثبت کنید. اگر گزارش با انتظار تراکنشی طولانی طراحی شده، نباید فرض شود انتقال آن از primary به standby همیشه بدون تغییر رفتار است. نیاز تازگی داده و تحمل قطع پرسوجو باید از ابتدا روشن باشد.
اگر برنامه بلافاصله پس از نوشتن، خواندن را به standby بفرستد، ممکن است نتیجه تازه هنوز قابل مشاهده نباشد. این مشکل با سالم بودن هر دو پایگاه داده نیز رخ میدهد. مسیرهای حساس مانند نمایش تأیید سفارش باید راهبرد مشخص داشته باشند؛ مثلاً خواندن وابسته به همان عملیات از منبع مناسب انجام شود. تصمیم باید در لایه برنامه و مسیریابی داده طراحی شود. افزایش سختافزار ممکن است فاصله را کم کند، اما قرارداد سازگاری را به طور خودکار تغییر نمیدهد.
failover بیش از ارتقای یک فرایند است
هنگام قطع primary، ابتدا باید خطر وجود دو نویسنده بررسی شود. اگر گره قدیمی هنوز بخشی از شبکه را میبیند و درخواست میپذیرد، ارتقای گره دیگر بدون جداسازی میتواند دو تاریخچه متفاوت بسازد. سازوکار انتخاب رهبر، قطع دسترسی نویسنده قدیمی و مسیریابی کلاینتها باید هماهنگ باشند. ابزار اجرای ارتقا فقط یک بخش فرایند است. در مانور، قطع شبکه را از خاموش شدن کامل میزبان جدا آزمایش کنید، چون در حالت اول امکان زنده ماندن هر دو سمت وجود دارد.
پس از ارتقا، اتصالهای برنامه باید به مقصد درست برگردند و گرههای باقیمانده مسیر جدید را دنبال کنند. primary قدیمی را بدون بررسی دوباره به عنوان نویسنده وارد نکنید. بازهمگامسازی ممکن است به روش خاص یا پایه تازه نیاز داشته باشد. زمان بازیابی را از دید برنامه اندازه بگیرید: اولین نوشتن موفق و خواندن سازگار مهمتر از زمان اجرای فرمان ارتقاست. همچنین خطاهای مبهم کلاینت را بررسی کنید؛ اگر نتیجه تراکنش برای برنامه نامعلوم است، تکرار باید با منطق جلوگیری از عملیات تکراری هماهنگ باشد.
تکثیر جای پشتیبان مستقل را نمیگیرد
حذف اشتباه جدول یا تغییر نامطلوب میتواند به standby نیز برسد. بنابراین تاریخچه بازیابی و پشتیبان مستقل همچنان لازم است. یک آزمایش بازیابی به زمان مشخص با داده آزمایشی انجام دهید و سپس صحت منطقی برنامه را بررسی کنید. در گزارش، نقطه بازیابی داده و زمان بازگشت سرویس را جدا بنویسید. این دو عدد به دو پرسش متفاوت پاسخ میدهند. سامانهای که سریع برمیگردد ولی داده زیادی از دست میدهد با سامانهای که دیرتر اما با داده تازهتر برمیگردد یک قرارداد عملیاتی ندارد.
برای نگهداری روزمره، فهرست standbyها و slotها را با داراییهای واقعی تطبیق دهید. مقصدی که ماهها قبل حذف شده نباید بدون دلیل همچنان نگهداری WAL ایجاد کند. در مقابل، standby جدید باید مالک و نقش مشخص داشته باشد: گزارشگیری، مقصد همگام یا نامزد بازیابی. این نقشها ممکن است تنظیمات متفاوت بخواهند. ثبت نقش در کنار نشانی و نسخه، هنگام حادثه کمک میکند تیم نخستین گره در دسترس را بدون ارزیابی تازگی و صلاحیت به نویسنده تبدیل نکند.