Client VPN به کلاینت یک آدرس می‌دهد، دست‌دادن کامل می‌شود و اتصال همچنان به جایی نمی‌رسد. پیش از دست‌زدن به گواهی‌ها یا نسخه‌های کلاینت، به جدول مسیرهای خود نقطه پایانی نگاه کنید. نقطه پایانی AWS Client VPN بسته را تنها زمانی ارسال می‌کند که یکی از مسیرهایش پیشوند مقصد را پوشش دهد؛ اگر چیزی منطبق نشود، بسته در نقطه پایانی دور ریخته می‌شود و میزبان مقصد هرگز SYN نمی‌بیند.

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

نقطه پایانی تنها چیزی را ارسال می‌کند که جدول مسیرهایش پوشش می‌دهد

هر مسیر یک CIDR مقصد به‌علاوه زیرشبکه‌ای است که باید ترافیک را دریافت کند. نقطه پایانی مقصد کلاینت را با آن فهرست مقایسه می‌کند، ورودی منطبق را برمی‌گزیند و بسته را به زیرشبکه مرتبط می‌فرستد. نبود ورودی یعنی نبود گام بعدی.

توجه کنید که مسیر چه نیست. ورودی جدول مسیرهای VPC نیست و چیزی را مجاز نمی‌کند. قواعد مجوز تعیین می‌کنند که آیا گروهی می‌تواند به مقصدی برسد؛ مسیرها تعیین می‌کنند که آیا نقطه پایانی جایی برای فرستادن بسته دارد. هر دو باید هم‌خوان باشند و با نشانه‌های متفاوت شکست می‌خورند، پس حدس‌زدن درباره اینکه کدام خراب است یک بعدازظهر را هدر می‌دهد.

ناسازگاری کلاسیک یک VPC هم‌تابه است. کسی مسیری برای 10.20.0.0/24 اضافه می‌کند در حالی که میزبان در 10.20.4.0/24 قرار دارد، بنابراین آدرس بیرون از هر ورودی می‌افتد. یک ضبط در سمت کلاینت SYNهای تکراری بدون پاسخ نشان می‌دهد و گزارش‌های مقصد هیچ چیزی نشان نمی‌دهند.

پیش از گواهی، فهرست مسیرها را بخوانید

مسیرهای نقطه پایانی شیء مستقل هستند، پس به‌جای خواندن جدول VPC مستقیم از آن‌ها بپرسید:

aws ec2 describe-client-vpn-routes --client-vpn-endpoint-id cvpn-endpoint-0123456789abcdef0 --query 'Routes[].{Dest:DestinationCidr,Target:TargetSubnet,Origin:Origin}'

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

یک منبع برای هر مقصد با for_each

بلوک‌های مسیر دست‌نویس همان لحظه‌ای که کسی پیشوندی را در کنسول اضافه می‌کند پراکنده می‌شوند. مقصدها را در یک نقشه نگه دارید و برای هر کلید یک منبع بسازید تا هر افزودن یا حذف جدا بماند.

variable "client_vpn_routes" {
  type = map(string)
  default = {
    "10.20.0.0/16"  = "subnet-0aa11bb22cc33dd44"
    "172.31.0.0/20" = "subnet-0aa11bb22cc33dd44"
  }
}

resource "aws_ec2_client_vpn_route" "this" {
  for_each               = var.client_vpn_routes
  client_vpn_endpoint_id = var.client_vpn_endpoint_id
  destination_cidr_block = each.key
  target_vpc_subnet_id   = each.value
  depends_on             = [aws_ec2_client_vpn_network_association.this]
}

وابستگی به انجمن شبکه را حفظ کنید. مسیر به زیرشبکه مرتبط نیاز دارد، پس applyی که هر دو را می‌سازد باید ابتدا انجمن را مرتب کند، و بدون آن ارجاع Terraform آزاد است مسیر را اول امتحان کند. سپس طرح را بخوانید: تعداد افزودن مسیرها باید با پیشوندهایی که اضافه کردید برابر باشد. اگر طرح نقطه پایانی را هم جایگزین کند، منبع نقطه پایانی غلط نوشته شده است و اعمال آن هر کلاینت متصل را قطع می‌کند.

پذیرفتن نقطه پایانی که خودتان نساخته‌اید

بیشتر تیم‌ها نقطه پایانی را به ارث می‌برند که در کنسول ساخته شده، و به همین دلیل هیچ کد مسیری وجود ندارد. فقط برای آوردن مسیرها به Terraform نقطه پایانی دوم برپا نکنید.

در عوض import کنید، یا شناسه‌ها را به‌عنوان متغیر بفرستید و اشیای به‌ارث‌رسیده را بدون مدیریت رها کنید. import به قالب شناسه‌ای نیاز دارد که ارائه‌دهنده برای هر نوع منبع مستند می‌کند؛ آن قالب نقطه پایانی، پیشوند مقصد و زیرشبکه هدف را رمزگذاری می‌کند. آن رشته را از مستندات منبع کپی کنید نه از حافظه بسازید، یک طرح اجرا کنید و پیش از افزودن چیز تازه انتظار هیچ تغییری نداشته باشید.

بسته را به ترتیبی که حرکت می‌کند دنبال کنید

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

  1. مسیر: پیشوندی مقصد را پوشش می‌دهد و به زیرشبکه‌ای مرتبط با نقطه پایانی اشاره می‌کند.
  2. مجوز: قاعده مجوز آن مقصد را برای گروه کاربر مجاز می‌کند. مسیر به‌تنهایی هرگز دسترسی نمی‌دهد.
  3. مسیر بازگشت: جدول مسیرهای زیرشبکه مقصد پاسخ‌ها را به‌سوی نقطه پایانی برمی‌گرداند و گروه امنیتی پورت را از استخر آدرس‌های کلاینت مجاز می‌کند.
  4. برنامه: یک اتصال واقعی TCP از کلاینت باز کنید، سپس تأیید کنید که گزارش‌های مقصد آدرس مبدأ مورد انتظار از استخر را نشان می‌دهند.

در هر apply یک پیشوند را تغییر دهید، سپس فهرست مسیرها را دوباره بخوانید و مقصد، قاعده مجوزدهنده و مسیر بازگشت را با هم ثبت کنید. نفر بعدی که اتصال ردشده را اشکال‌زدایی می‌کند باید از همین فهرست شروع کند، نه از نظریه‌ای درباره گواهی‌ها.

مقالات مرتبط