Я не думаю, что есть однозначный правильный ответ на ваш вопрос. Вместо этого существует множество способов приблизиться к желаемому. Поэтому я дам несколько советов, как это сделать.
Если на машине более 2 интерфейсов ( lo
считается за один), у вас возникнут проблемы с автоматическим определением нужного интерфейса. Вот несколько рецептов, как это сделать.
Проблема, например, в том, что хосты находятся в DMZ за брандмауэром NAT, который меняет общедоступный IP-адрес на какой-то частный и пересылает запросы. У вашей машины может быть 10 интерфейсов, но только один соответствует общедоступному.
Даже автоматическое определение не работает, если вы используете двойной NAT, когда ваш брандмауэр даже переводит исходный IP-адрес во что-то совершенно другое. Таким образом, вы даже не можете быть уверены, что маршрут по умолчанию ведет к вашему интерфейсу с общедоступным интерфейсом.
Обнаружить его по маршруту по умолчанию
Это мой рекомендуемый способ автоматического обнаружения вещей
Что-то вроде ip r get 1.1.1.1
обычно сообщает вам интерфейс, у которого есть маршрут по умолчанию.
Если вы хотите воссоздать это на своем любимом языке сценариев / программирования, используйте strace ip r get 1.1.1.1
и следуйте по дороге из желтого кирпича.
Установите его с помощью /etc/hosts
Это моя рекомендация, если вы хотите сохранить контроль
Вы можете создать запись /etc/hosts
как
80.190.1.3 publicinterfaceip
Затем вы можете использовать этот псевдоним publicinterfaceip
для ссылки на свой общедоступный интерфейс.
К сожалению haproxy
, не разбирается в этом трюке с IPv6
Используйте окружающую среду
Это хороший обходной путь, /etc/hosts
если вы неroot
То же, что и /etc/hosts
. но используйте для этого среду. Вы можете попробовать /etc/profile
или ~/.profile
для этого.
Следовательно, если вашей программе нужна переменная, MYPUBLICIP
вы можете включить такой код (это C, не стесняйтесь создавать C ++ из него):
#define MYPUBLICIPENVVAR "MYPUBLICIP"
const char *mypublicip = getenv(MYPUBLICIPENVVAR);
if (!mypublicip) { fprintf(stderr, "please set environment variable %s\n", MYPUBLICIPENVVAR); exit(3); }
Итак, вы можете назвать свой скрипт / программу /path/to/your/script
следующим образом
MYPUBLICIP=80.190.1.3 /path/to/your/script
это работает даже в crontab
.
Перечислите все интерфейсы и удалите те, которые вам не нужны
Отчаянный способ, если вы не можете использовать ip
Если вы знаете, чего не хотите, вы можете перечислить все интерфейсы и игнорировать все ложные.
Кажется, здесь уже есть ответ https://stackoverflow.com/a/265978/490291 для этого подхода.
Сделайте это как DLNA
Путь пьяного, пытающегося утопиться в алкоголе
Вы можете попробовать перечислить все шлюзы UPnP в вашей сети и таким образом найти правильный маршрут для какой-то «внешней» вещи. Это может быть даже на маршруте, на который не указывает ваш маршрут по умолчанию.
Подробнее об этом, возможно, см. Https://en.wikipedia.org/wiki/Internet_Gateway_Device_Protocol.
Это дает вам хорошее представление о том, какой из них является вашим настоящим общедоступным интерфейсом, даже если ваш маршрут по умолчанию указывает в другом месте.
Есть даже больше
Где гора встречает пророка
Маршрутизаторы IPv6 рекламируют себя, чтобы дать вам правильный префикс IPv6. Глядя на префикс, вы подскажете, какой у него внутренний IP-адрес или глобальный.
Вы можете прослушивать кадры IGMP или IBGP, чтобы найти подходящий шлюз.
Имеется менее 2 ^ 32 IP-адресов. Следовательно, в локальной сети не требуется много времени, чтобы просто пропинговать их все. Это дает вам статистическую информацию о том, где с вашей точки зрения расположена большая часть Интернета. Однако вы должны быть немного разумнее, чем знаменитый https://de.wikipedia.org/wiki/SQL_Slammer
ICMP и даже ARP - хорошие источники информации о боковой полосе сети. Это также может помочь вам.
Вы можете использовать широковещательный адрес Ethernet для связи со всеми устройствами сетевой инфраструктуры, которые часто помогают, например, DHCP (даже DHCPv6) и так далее.
Этот дополнительный список, вероятно, бесконечен и всегда неполон, потому что каждый производитель сетевых устройств усердно изобретает новые дыры в безопасности, чтобы автоматически определять свои собственные устройства. Что часто очень помогает в том, как обнаружить публичный интерфейс там, где его не должно быть.
'Достаточно. Вне.