Python не получает IP, если кабель подключен после запуска скрипта
Я надеюсь, что это не пересекает территорию суперпользователя.
Итак, у меня есть встроенный linux, где системные процессы, естественно, довольно раздеты. Я не совсем уверен, какой системный процесс отслеживает физический уровень и запускает клиент DHCP, когда сетевой кабель подключен, но я сам его создал. Is Проблема в том, что если у меня есть скрипт на Python, использующий http-соединения и работающий до того, как у меня есть IP-адрес, он никогда не получит соединение. Даже после того, как у меня есть действующий IP, питон все еще имеет
"Временная ошибка в разрешении имени"
Итак, как я могу заставить python реализовать новое доступное соединение без перезапуска скрипта?
В качестве альтернативы, я пропускаю некоторые нормальные процедуры, которые Linux работает нормально при подключении к сетевому кабелю.
Я использую клиент dhcp udhcpc, а версия python 2.6. Использование httplib для соединений.
3 ответа
Похоже, httplib кэши /etc/resolv.conf
который обновляется после того, как ваш клиент DHCP получает IP.
Возможно, вы захотите написать скрипт-обертку, который ожидает получения IP-адреса, а затем вызывает ваш скрипт на python.
Кроме того, вы можете попытаться в вашем скрипте Python не открывать какие-либо сокетные соединения, пока вы не получите IP-адрес и не /etc/resolv.conf
обновлено.
редактировать
httplib использует socket.create_connection()
который после некоторого поиска нашел кеш /etc/resolv.conf
, (Ну, похоже, что встроенная версия libc фактически выполняет кеширование).
Вы можете попробовать решение SugarLabs, хотя я не могу говорить о его эффективности.
Может случиться так, что один из модулей python кэширует состояние сети, и поэтому он не использует последние настройки. Попробуйте перезагрузить все модули, связанные с сетью. Простой пример этого:
import sys, socket, urllib
for i in [sys, socket, urllib]:
reload(i)
если это не сработает, оглянись в sys.modules
чтобы увидеть, что еще было импортировано, и попробуйте больше модулей там. Более экстремальной версией перезагрузки был бы приведенный ниже код, который вы можете попробовать в качестве последней попытки.
код
import sys
print 'reloading %s modules ' % len(sys.modules)
for name, module in sys.modules.items():
try:
reload(module)
except:
print 'failed to import %s' % name
выход
reloading 42 modules
failed to import __main__
failed to import encodings.encodings
failed to import encodings.codecs
failed to import lazr
failed to import encodings.__builtin__
После долгих исследований проблема glibc, предложенная Джедвардсом, казалась проблемой. Я не нашел решения, но сделал обходной путь для моего варианта использования. Учитывая, что я использую только один URL, я добавил свой собственный resolv.file. Небольшой демон получает IP-адрес URL, когда PHY сообщает о подключенном кабеле. Этот IP-адрес сохраняется в "моем собственном resolv.conf". Из этого файла скрипт Python извлекает IP-адрес, который будет использоваться для сообщений.
Не очень хорошее решение, но решение.