我的应用程序具有Flask后端和Angular / Electron前端。该应用程序可在Mac Catalina上本地运行。 Flask,Celery和Redis位于单独的Docker容器中,而前端位于Docker外部。 Flask容器正在端口0.0.0.0:5078上侦听。我已将CORS策略设置为仅允许来自前端的“ 127.0.0.1:4200”中的消息。无需互联网连接。后端容器将通过模拟终端命令由前端启动。我将在非技术用户的Catalina MacBooks上远程安装该应用程序。
问题:根据Docker might be exposing ports to the world,Beware of exposing ports in Docker和Docker not blocked by macOS firewall的说法,这种使用0.0.0.0:5078构成安全威胁。我该如何解决这种威胁,例如通过阻止与此端口的任何外部连接?
这是一些python 3.8代码
# imports: waitress, flask_cors, blueprint
cors = CORS(blueprint, resources={r"/*": {"origins":["http://127.0.0.1:4200"]}})
if __name__ == "__main__":
serve(flask_app, host= '0.0.0.0', port=5078, threads=8)
这是Dockerfile:
FROM python:3.8.3-slim-buster
WORKDIR /app
COPY requirements.txt requirements.txt
ENV BUILD_DEPS="build-essential" \
APP_DEPS="curl libpq-dev"
RUN apt-get update \
&& apt-get install -y ${BUILD_DEPS} ${APP_DEPS} --no-install-recommends \
&& pip install --default-timeout=10000 -r requirements.txt
ARG FLASK_ENV="development"
ENV FLASK_ENV="${FLASK_ENV}" \
FLASK_APP="back5x.api.app" \
PYTHONUNBUFFERED="true"\
FLASK_DEBUG=1
COPY . .
RUN ["chmod", "+x", "/app/docker-entrypoint.sh"]
ENTRYPOINT ["/app/docker-entrypoint.sh"]
EXPOSE 5078
CMD ["python", "main.py"]
和docker-compose:
version: "3.8"
services:
redis:
# ...
web:
build:
context: "."
args:
- "FLASK_ENV=development"
depends_on:
- "redis"
- "worker"
env_file:
- ".env"
environment:
FLASK_DEBUG: 1
FLASK_APP: back5x.api.app.py
healthcheck:
test: "${DOCKER_HEALTHCHECK_TEST:-curl localhost:5078/healthy}"
...
ports:
- "5078:5078"
restart: "unless-stopped"
volumes:
- ".:/app"
worker: #celery worker
...
volumes:
redis: {}
尝试过: 我发现基于Docker的解决方案使用Linux iptables,例如Disallow egress from Docker containers on Docker for Mac和上述参考。所以我将这些添加到了Dockerfile中:
RUN apt-get install -y iptables --no-install-recommends #after pip install
RUN iptables -N DOCKER-USER #after COPY . .
RUN iptables -I FORWARD -j DOCKER-USER
RUN iptables -A DOCKER-USER -j RETURN
RUN iptables -I DOCKER-USER -i eth0 ! -s 0.0.0.0 -j DROP
没有中间三行,我得到一个错误,即找不到DOCKER-USER。和他们在一起,我必须以root身份运行。我已经尝试过特权模式和app_cap
,但是由于我是Docker的新手,所以我没有这个功能。
我还研究了在Mac的PF防火墙中定义一个规则,以阻止与该端口的外部连接。但是,这对于要使用我的应用程序的人来说并不理想。类似的情况是安装付费的“ Little Snitch”应用。
在走这条路线之前,可能有基于代码或基于Docker的解决方案吗? (或者也许有启动后端的适当命令?)
答案 0 :(得分:0)
一个有效的解决方案基于David Maze和Matt的评论以及此question。这些是步骤:
"ip": "127.0.0.1"
添加到json配置文件中。ports
服务的 "127.0.0.1:5078:5078"
设置为web
。0.0.0.0
当我检查时,来自Electron的localhost 4201的消息通过了。另外,运行 netstat -anvp tcp | awk 'NR<3 || /LISTEN/
显示不安全的端口0.0.0.0.5078
不再暴露于外部。
`