Почему я не могу выполнить команду ping для приложения, запущенного в Docker?

Я работаю на Windows 10, если это важно. Я создал следующий пример кода: 
<pre><code class="python">import uvicorn
from fastapi import FastAPI

app = FastAPI()

@app.get("/")
async def root():
    return {
        "Hello world!"
    }

if __name__ == "__main__":
    uvicorn.run(
        app="main:app",
        port=7771,
        reload=True,
    )</code></pre> 
Запустив локально, всё работает, и я могу подключаться по адресу 127.0.0.1:7771. 
Однако, когда я запускаю `docker compose -f "compose.yaml" up -d --build` в VS Code, сервер внутри контейнера работает, но я не могу подключиться к нему по адресу 127.0.0.1:7771. 
В браузере отображается сообщение: 
<pre><code>Страница недоступна
Сайт localhost не отправил данных.
ERR_EMPTY_RESPONSE</code></pre> 
Можете пояснить, в чём может быть проблема?
  • 10 октября 2024 г. 10:14
Ответы на вопрос 3
Проблема, с которой вы столкнулись, скорее всего связана с конфигурацией контейнера Docker и тем, как он управляет сетевыми соединениями. Когда вы запускаете приложение внутри Docker-контейнера, оно "изолировано" в свою собственную сетевую среду. Чтобы получить доступ к вашему приложению с `localhost`, необходимо убедиться в нескольких моментах:

1. **Проверка портов в Dockerfile или docker-compose.yml**: Убедитесь, что вы правильно настроили порты в вашем `docker-compose.yml` файле. Например, если ваш FastAPI-сервер слушает на порту 7771, нужно убедиться, что этот порт правильно проксируется наружу.

   Пример секции `services` в вашем `compose.yaml`:

   ```yaml
   version: '3.8'
   services:
     app:
       build: .
       ports:
         - "7771:7771"
   ```

   Здесь `7771:7771` означает, что порт 7771 вашего контейнера (внутренний) будет доступен на порту 7771 вашего хоста (внешний).

2. **Настройка Uvicorn**: По умолчанию Uvicorn может слушать только на `127.0.0.1` внутри контейнера, что указывает, что он не принимает соединения извне. Для этого необходимо указать `host` как `0.0.0.0`, чтобы он принимал соединения на всех интерфейсах. Измените вашу функцию запуска на:

   ```python
   if __name__ == "__main__":
       uvicorn.run(
           app="main:app",
           host="0.0.0.0",  # Добавленный параметр
           port=7771,
           reload=True,
       )
   ```

3. **Используйте правильный адрес**: После того как вы примените изменения, запустите Docker контейнер снова и попробуйте получить доступ к вашему приложению по адресу `http://localhost:7771`.

4. **Проверка сетевых настроек Docker**: Если вы по-прежнему не можете подключиться, проверьте, есть ли другие приложения, использующие порт 7771. Вы можете также проверить настройки брандмауэра Windows.

После выполнения этих шагов приложение должно быть доступно по адресу `127.0.0.1:7771`. Если возникнут дополнительные проблемы, дайте знать, и мы попробуем разобраться дальше!
Проблема была в этом: 
if __name__ == "__main__":
    uvicorn.run(
        app="main:app",
        port=7771,
        reload=True,
    )

Надо чтобы был указан хост 0.0.0.0
После этого по localhost:7771 я смог подключиться
как вариант в compose поставить driver как host network - так даже лучше будет 

https://docs.docker.com/engine/network/drivers/
https://docs.docker.com/reference/compose-file/net...
Похожие вопросы