4.7 KiB
IP multicast
Один контейнер принимает UDP-датаграммы на порту 9999 и пересылает их на multicast-адрес 224.0.2.0:10000. Три контейнера-получателя присоединяются к этой группе и печатают полученные сообщения. В примере нет подтверждений, повторной передачи и восстановления пропусков.
Запуск
Из корня репозитория перейдите в каталог примера и запустите контейнеры:
cd materials/04-group-comm/seminar/ip_multicast
docker compose up --build -d
docker compose logs -f sender receiver1 receiver2 receiver3
Дождитесь сообщения ready от отправителя и каждого получателя. Последняя команда показывает журналы и занимает терминал. Следующие команды выполняйте во втором терминале из того же каталога.
Отправьте пробное сообщение через Python 3:
python -c "import socket; s=socket.socket(socket.AF_INET,socket.SOCK_DGRAM); s.sendto(b'probe',('127.0.0.1',9999)); s.close()"
При необходимости замените python на имя Python 3 в своём окружении. Убедитесь, что probe появился в журналах всех трёх получателей. Отправитель также печатает каждую пересылку. Имена сервисов в журнале позволяют различить получателей.
Если с хоста сообщения не доходят (нет forwarded), отправляйте из контейнера: docker compose exec sender python -c "...".
Эксперимент: получатель пропустил сообщение
До запуска предположите, какие получатели увидят m1 и m2 и получит ли вернувшийся участник пропущенные данные.
-
Остановите третьего получателя:
docker compose stop receiver3 -
Отправьте
m1:python -c "import socket; s=socket.socket(socket.AF_INET,socket.SOCK_DGRAM); s.sendto(b'm1',('127.0.0.1',9999)); s.close()" -
Верните третьего получателя:
docker compose start receiver3 -
Дождитесь нового сообщения
readyотreceiver3и снова отправьтеprobe. Убедитесь, что третий получатель его видит. -
Отправьте
m2, заменив в командеb'm1'наb'm2'.
При штатной работе стенда m1 увидят первый и второй получатели, а m2 — все три. Третий получатель не получит m1 задним числом: программа не хранит историю и не запрашивает пропущенные сообщения. UDP допускает потери и без отключения получателя; успешная проба не является доказательством гарантированной доставки.
Обсудите:
- Какие действия выполняет
IP_ADD_MEMBERSHIPи где задаётся адрес группы? - Где в программе можно было бы добавить подтверждения или восстановление пропусков?
- Почему получение сетевого пакета и надёжная доставка сообщения приложению — разные события?
Пустая UDP-датаграмма тоже является сообщением: b'' не означает закрытие соединения. Можно отправить её и затем обычное сообщение, чтобы проверить, что оба процесса продолжают работу.
Повторный запуск контейнера в этом эксперименте иллюстрирует пропуск данных. В домашнем задании используется модель crash-stop: отказавшие процессы не возвращаются.
Завершение
Остановите просмотр журналов сочетанием Ctrl+C, затем удалите контейнеры стенда:
docker compose down