مقالات

من یک خط لوله انتقال پایگاه داده بدون اختلال ایجاد کردم (PostgreSQL به Aurora)


TL; DR: من با استفاده از AWS DMS، Terraform و اسکریپت‌های اعتبارسنجی خودکار، یک چارچوب آماده تولید برای انتقال پایگاه‌های داده PostgreSQL به Aurora با زمان توقف صفر ایجاد کردم.

مشکل

سال گذشته پروژه‌ای را به ارث بردم که روی PostgreSQL خود مدیریتی اجرا می‌شد. پایگاه داده به 500 گیگابایت افزایش یافته بود و ما زمان زیادی را صرف تعمیر و نگهداری می کردیم: وصله ها، پشتیبان گیری، مشکلات تکرار، سردردهای معمول. تصمیم برای انتقال به Aurora PostgreSQL برای عملیات مدیریت شده، مقیاس پذیری بهتر و ادغام AWS بومی گرفته شد.

گرفتن؟ این یک پایگاه داده تولیدی بود که به 50000 کاربر فعال روزانه خدمات رسانی می کرد. هرگونه خرابی به معنای از دست دادن درآمد و عصبانیت مشتریان بود. کسب و کار به ما یک پنجره پشتیبانی از… صفر دقیقه داد. بدون فشار

اولین چیزی که من امتحان کردم (و چرا کار نکرد)

فکر اولیه من ساده بود: pg_dump و pg_restore در یک دوره آرام. رویکرد کلاسیک، درست است؟

# The naive approach
pg_dump -Fc production_db > backup.dump
pg_restore -d aurora_target backup.dump
وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

برای یک پایگاه داده 500 گیگابایتی، بسته به اندازه شبکه و نمونه، تقریباً 4 تا 6 ساعت طول می کشد. این یعنی 4 تا 6 ساعت داده‌های قدیمی که در منبع جمع می‌شوند و کاربران همچنان به تایپ کردن ادامه می‌دهند. غیر قابل قبول

من همچنین به تکرار منطقی بومی PostgreSQL نگاه کردم، اما راه‌اندازی انتشار/اشتراک در حساب‌های AWS با کنترل‌های امنیتی مناسب در حال تبدیل شدن به یک هیولا بود. همچنین، ابزارهای عملیاتی اطراف آن اساساً DIY بودند.

سپس AWS DMS را پیدا کردم. این کار کارهای سنگین را انجام می دهد: بار کامل به علاوه ضبط داده های تغییر در یک سرویس مدیریت شده. چالش ایجاد همه چیز در اطراف آن بود تا مهاجرت ها تکرار شونده و ایمن شوند.

راه حل

من یک چارچوب مهاجرت کامل با چهار جزء اصلی ایجاد کرده ام:

  1. ماژول های زمینی برای کل زیرساخت AWS
  2. اسکریپت های اتوماسیون پایتون اعتبار سنجی و لغو
  3. گردش‌های کاری GitHub Actions برای CI/CD
  4. CloudWatch مانیتورینگ برای دید کامل

نمای کلی معماری

استراتژی سبز-آبی به شرح زیر عمل می کند: DMS بار کاملی از تمام داده های موجود را انجام می دهد، سپس برای ثبت تغییرات فعلی به حالت CDC تغییر می کند. هر دو پایگاه داده تا زمانی که ما آماده سقط شویم، همگام می مانند.

زیرساخت های زمینی

من یک Terraform مدولار برای تکرارپذیری در محیط های مختلف ایجاد کردم. ماژول DMS به این صورت است:

module "dms" {
  source = "./modules/dms"

  project     = "db-migration"
  environment = "prod"

  subnet_ids         = var.private_subnet_ids
  security_group_ids = [module.networking.dms_security_group_id]

  replication_instance_class = "dms.r5.4xlarge"
  multi_az                   = true

  source_db_host     = var.source_db_host
  source_db_username = var.source_db_username
  source_db_password = var.source_db_password

  target_db_host     = module.aurora.cluster_endpoint
  target_db_username = var.aurora_master_username
  target_db_password = var.aurora_master_password
}
وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

ماژول DMS ایجاد می کند:

  • یک نمونه تکرار با اندازه مناسب
  • منبع و نقطه پایانی هدف با پیکربندی مناسب SSL
  • کار تکرار با CDC فعال است
  • CloudWatch برای نظارت بر تأخیر و خطاها هشدار می دهد

اسکریپت های اعتبار سنجی

قبل از هرگونه قطعی، باید اطمینان داشته باشید که داده ها مطابقت دارند. من یک چک کننده پایتون نوشتم که چندین بعد را بررسی می کند:

# Quick validation (uses table statistics for fast estimates)
python validation.py --quick

# Full validation (exact counts, checksums, sequence values)
python validation.py --full

# Just check DMS status
python validation.py --dms
وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

اعتبار سنجی کامل انجام می دهد:

آن را بررسی کنید توضیحات
ردیف ها را بشمار تعداد دقیق ردیف ها را بین منبع و هدف مقایسه کنید
جمع های چک هش MD5 از داده های نمونه از هر جدول
دنباله ها بررسی کنید که مقادیر توالی همگام باشند
کلیدهای اصلی مطمئن شوید که همه جداول دارای PK هستند (برای CDC لازم است)
وضعیت DMS کار در حال اجرا است، تاخیر تکرار زیر آستانه است

در اینجا یک قطعه از تأیید جمع‌بندی چک آمده است:

def calculate_checksum(self, table: str, columns: list, limit: int = 1000) -> str:
    """Calculate MD5 checksum of sample rows."""
    cols = ", ".join(columns)
    query = f"""
        SELECT md5(string_agg(row_hash, '' ORDER BY row_hash))
        FROM (
            SELECT md5(ROW({cols})::text) as row_hash
            FROM {table}
            ORDER BY {columns[0]}
            LIMIT {limit}
        ) t
    """
    result = self.execute_query(query)
    return result[0][0] if result else None
وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

روند وقفه

Cutover جایی است که همه چیز اعصاب خردکن می شود. من یک فرآیند چند فازی با قابلیت بازگشت خودکار در هر مرحله ایجاد کردم:

فاز اقدام برگشت در دسترس است
1 پیش اعتبارسنجی (بررسی DMS، تعداد ردیف) بله
2 منتظر همگام سازی باشید (تاخیر CDC زیر آستانه) بله
3 اتصالات تخلیه (اتصالات منبع پایانی) بله
4 همگام سازی نهایی (منتظر تغییرات باقی مانده باشید) بله
5 تکرار را متوقف کنید فقط به صورت دستی
6 پس از تأیید اعتبار فقط به صورت دستی

اسکریپت لغو وضعیت را پس از هر مرحله در JSON ذخیره می‌کند، بنابراین اگر مشکلی انجام نشد، می‌توانید ادامه دهید:

# Always do a dry run first
python cutover.py --dry-run

# Execute when ready
python cutover.py --execute

# Resume from saved state if interrupted
python cutover.py --execute --resume
وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

ادغام GitHub Actions

همه چیز از طریق GitHub Actions خودکار می شود. گردش کار حمل و نقل برای تولید به تأیید دستی نیاز دارد:

jobs:
  approval:
    name: Approve Cutover
    runs-on: ubuntu-latest
    if: github.event.inputs.mode == 'execute'
    environment: prod-cutover  # Requires manual approval
    steps:
      - name: Cutover Approved
        run: echo "Cutover approved"

  cutover:
    name: Database Cutover
    needs: [approval]
    # ... actual cutover steps
وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

گردش کار اعتبارنامه‌ها را از AWS Secrets Manager دانلود می‌کند، اسکریپت انتقال را اجرا می‌کند، مصنوعات حالت را برای ممیزی آپلود می‌کند، و اعلان‌های SNS را در صورت شکست ارسال می‌کند.

نتایج

انتقال با معیارهای زیر با موفقیت انجام شد:

متریک ارزش
کل داده منتقل شد 512 گیگابایت
زمان مهاجرت (بار کامل) 3 ساعت 22 دقیقه
تأخیر CDC در هنگام قطع 2.1 ثانیه
برنامه را متوقف کنید 0 ثانیه
خطاهای اعتبارسنجی داده ها 0

پس از مهاجرت مشاهده می کنیم:

  • کاهش تأخیر خواندن 40 درصد (کپی‌های خواندنی Aurora)
  • زمان صرف شده برای نگهداری پایگاه داده صفر است
  • پشتیبان گیری و بازیابی خودکار در یک لحظه

درس های آموخته شده

1. اسکریپت های اعتبارسنجی خود را به دقت تست کنید. در ابتدا با یک اشکال مواجه شدم که در آن کوئری چک‌جمع به درستی مقادیر NULL را مدیریت نمی‌کرد. خوشبختانه سر صحنه فیلمبرداری او را گرفتم.

2. کپی DMS خود را به اندازه مناسب تنظیم کنید. ما با dms.r5.2xlarge شروع کردیم و در حین بارگذاری کامل به محدودیت های CPU رسیدیم. ارتقاء به 4xlarge زمان مهاجرت را به نصف کاهش می دهد.

3. عقب مانده CDC را با وسواس نظارت کنید. زنگ‌های CloudWatch را برای تاخیرهای بیش از 30 ثانیه تنظیم کردم. در طول مهاجرت، زمانی که شخصی یک کار دسته جمعی را در منبع شروع کرد، حداکثر تا 45 ثانیه داشتیم. دانستن این موضوع بلافاصله به ما اجازه داد تا قطعی را به تعویق بیندازیم تا رفع شود.

4. شما یک طرح بازگشتی دارید که در واقع آن را آزمایش کرده اید. ما منبع PostgreSQL را تا 48 ساعت پس از قطع شدن فعال نگه داشتیم. هنگامی که یک اشکال کوچک (غیر مرتبط با مهاجرت) ظاهر شد، داشتن یک گزینه بازگشت به همه باعث آرامش در هنگام بررسی شد.

5. بیش از آنچه لازم می دانید ارتباط برقرار کنید. ما در طول مهاجرت هر ساعت به روز رسانی می فرستادیم. ذینفعان از شفافیت قدردانی کردند.

خودتان آن را امتحان کنید

چارچوب کامل در GitHub در دسترس است:

مخزن: github.com/mateenali66/zero-downtime-db-migration

شامل:

  • ماژول های Terraform برای DMS، Aurora، شبکه و نظارت
  • اعتبار سنجی پایتون و اسکریپت های شکست
  • گردش‌های کاری GitHub Actions
  • مستندات کامل و راندبوک

آن را شبیه سازی کنید، پیکربندی را برای محیط خود تطبیق دهید و قبل از اینکه تولید را لمس کنید، مرحله را طی کنید. مهاجرت مبارک


Source link

نوشته های مشابه

دیدگاهتان را بنویسید

دکمه بازگشت به بالا