Зберігати IP-адреси клієнтів VPN чи застосовувати SNAT на межі хмари
Збереження джерела зберігає особу клієнта в кожному журналі, SNAT тримає таблицю маршрутизації компактною. Три умови підкажуть, що потрібно застосунку.
Збереження адреси клієнта VPN аж до застосунку робить кожен рядок журналу й кожен запис у списку дозволених такими, що означають одне й те саме. Перезапис адреси на межі хмари спрощує таблицю маршрутизації та робить журнали менш корисними. Жоден із варіантів сам собою не є хибним, і аргумент, який його визначає, рідко стосується продуктивності. Вирішують три умови: чи має застосунок знати, яка людина підключилася, чи прийме хмарна тканина джерело, яке ви збираєтеся надіслати, і хто потім візьме на себе відповідальність за зворотний маршрут.
Вирішують три умови
Почніть із вимоги застосунку, а не з мережевої діаграми. Якщо авторизація або аудит залежать від адреси окремого клієнта, то її збереження є функціональною вимогою, а перетворення є регресом. Якщо застосунку потрібно знати лише те, що трафік прийшов шляхом віддаленого доступу, перетвореної адреси достатньо, і це значно дешевше в експлуатації.
Друга умова механічна. Віртуальна мережа не довіряє автоматично пакету, який заявляє адресу, не призначену інтерфейсу відправника. Більшість хмарних тканин цього вимагають, по-різному й під різними назвами, і проєкт, який це ігнорує, виглядатиме правильно на схемі й тихо губитиметься в продакшені.
Третя умова організаційна. Збереження джерел означає, що таблиця маршрутизації підмережі застосунку має вказувати назад на шлюз для префікса клієнта, і кожна команда, яка згодом додасть підмережу, повинна підтримувати цей маршрут узгодженим. Це невеликі витрати один раз і повторювані витрати на десятки акаунтів. Вирішіть, хто платить, перш ніж обіцяти таку поведінку.
Маршрут не є дозволом на підміну
Додавання зворотного маршруту повідомляє вашій підмережі, куди мають іти відповіді. Воно не повідомляє тканині, що екземпляру, який пересилає ці пакети, дозволено надсилати їх із чужим джерелом. В AWS відповідний контроль це перевірка джерела й призначення, і вона видима для кожного екземпляра:
aws ec2 describe-instances --instance-ids i-0a1b2c3d4e5f60718 \
--query "Reservations[].Instances[].SourceDestCheck"
aws ec2 modify-instance-attribute --instance-id i-0a1b2c3d4e5f60718 \
--no-source-dest-check
Вимкніть її лише для екземпляра, чия документована робота це пересилання, і ні для чого іншого. Кожна віртуальна машина застосунку, яка залишає перевірку ввімкненою, це на одну машину менше, яку можна використати для надсилання трафіку з позиченим джерелом. Якщо ваша платформа не AWS, шукайте еквівалентне налаштування анти-спуфінгу або дозволених адрес, а не припускайте, що поведінка перенесеться.
Швидке захоплення пакетів вирішує питання швидше, ніж читання консолі. Якщо відповіді виходять, а клієнт їх ніколи не бачить, то тканина відкидає підроблене джерело, а не застосунок зазнає невдачі.
Що купує перетворення і скільки воно коштує
Перезапис джерела на шлюзі усуває проблему зворотного шляху. Застосунок бачить одну адресу, до якої вже вміє звертатися, і префіксу клієнта ніколи не потрібно з'являтися в хмарній таблиці маршрутизації. У Linux правило складається з одного рядка, і варто написати найвужчий варіант, який ви можете:
sysctl -w net.ipv4.ip_forward=1
iptables -t nat -A POSTROUTING -s 172.20.8.0/24 -o ens5 -j SNAT --to-source 10.40.3.10
Зверніть увагу, що тепер записує застосунок: 10.40.3.10 для кожного користувача, при кожному підключенні, назавжди. Будь-який список дозволених адрес, побудований на цьому значенні, тепер дає доступ усій популяції віддаленого доступу, і будь-який розгляд інциденту має повертатися до шлюзу, щоб відповісти, хто це був.
Рішення не в тому, щоб відмовитися від перетворення, а в тому, щоб перестати вдавати, ніби адреса це особа. Несіть особу клієнта в автентифікованому полі, записуйте її на шлюзі разом із перетвореним кортежем і дозвольте застосунку з'єднуватися за ним. Без ключа з'єднання перетворення перетворює мережеву проблему на постійну криміналістичну.
Ретранслятор це інший інтерфейс
Зворотний проксі перед застосунком повністю обходить питання маршрутизованого шляху. Проксі відкриває власне з'єднання з бекендом, тому префіксу клієнта ніколи не потрібно бути маршрутизованим усередині віртуальної мережі, а застосунок може отримати особу в заголовку, який задає проксі.
Цей заголовок заслуговує довіри лише тоді, коли бекенд приймає його від проксі і ні від чого іншого. У термінах nginx це означає явно назвати довіреного партнера замість того, щоб вірити всьому, що надходить:
set_real_ip_from 10.40.3.10;
real_ip_header X-Forwarded-For;
real_ip_recursive on;
Будь-який клієнт, який може напряму досягти бекенду, може підробити той самий заголовок, тому бекенд має бути недоступним інакше, як через проксі. Це факт брандмауера, а не думка про конфігурацію, і саме це припущення люди пропускають, коли копіюють фрагмент.
Ретранслятор також змінює те, що ви купуєте. Ви отримуєте особу на рівні застосунку й природне місце, де її записувати; ви відмовляєтесь від універсальності, бо кожному новому протоколу потрібна власна підтримка проксі. Для служб HTTP цей обмін зазвичай добрий, а для всього, що не є HTTP, зазвичай зовсім недоступний.
Запишіть, що бачить кожна межа
Що б ви не обрали, огляд дизайну має завершуватися однією таблицею, яка називає адресу джерела й доказову особу на кожному переході. Без неї перший інцидент породжує три команди, кожна з яких описує іншого клієнта.
| Boundary | Source the next hop sees | What is actually proven |
|---|---|---|
| Client to gateway | 172.20.8.14 | A certificate or credential was presented |
| Gateway to app subnet, preserved | 172.20.8.14 | The same session, if the return route exists |
| Gateway to app subnet, translated | 10.40.3.10 | Only that traffic came through the gateway |
| Proxy to backend | 10.40.3.10 plus a header | The proxy asserted an identity it authenticated |
Потім виберіть. Зберігайте, коли авторизація застосунку справді залежить від адреси клієнта і ви можете взяти маршрут на себе. Перетворюйте, коли це не так і ви можете нести особу поза смугою, і використовуйте настанови AWS щодо екземплярів пересилання для специфічних для платформи налаштувань пересилання. Вдавайтеся до ретранслятора, коли служба говорить HTTP і ви хочете, щоб особа взагалі перестала бути адресою.