
云容笔谈·东方红颜影像生成系统企业级部署架构基于Docker与内网穿透方案最近和不少企业的技术负责人交流发现大家对AI影像生成系统很感兴趣但一提到部署尤其是既要保证内部数据安全又要让外部特定用户能访问就有点犯难。直接把系统放到公有云上担心数据泄露完全封闭在内网又无法满足远程协作或客户演示的需求。这让我想起了之前为一个设计团队部署“云容笔谈·东方红颜”影像生成系统的经历。他们需要在公司内部服务器上运行这套系统确保所有生成的人物形象、设计稿等核心数据不出内网但同时又需要让分布在不同城市的合作方设计师能安全地访问系统提交需求并查看生成效果。经过一番折腾我们最终敲定了一套基于Docker容器化和内网穿透技术的混合部署方案。今天我就把这套方案的思路和具体实践过程分享出来如果你也在为类似的问题寻找答案或许能给你一些启发。1. 企业部署的核心挑战与方案选型在开始动手之前我们得先搞清楚企业部署这类AI系统时到底在担心什么。抛开技术细节核心诉求其实就三点数据要安全、访问要可控、运维要简单。传统的做法要么是全部上云牺牲一部分数据安全感要么是拉专线成本高且不灵活。而我们采用的“内部部署安全外访”模式则试图在两者之间找到一个平衡点。它的核心思想是系统本体和所有数据牢牢锁在内网服务器上只通过一个加密的“安全通道”将特定的Web服务端口映射到公网。外部用户访问的其实是一个位于公网的“入口”这个入口通过加密隧道与内网的真实服务通信。为了实现这个目标我们的技术栈选型如下Docker Docker Compose用于封装应用及其所有依赖实现环境标准化和快速部署。这是保证“运维简单”的基础。Nginx作为反向代理服务器处理HTTPS、负载均衡如果需要和静态资源提升安全性和性能。内网穿透工具这是实现“安全外访”的关键。我们对比了frp和ngrok最终选择了frp主要因为它开源、可自建服务端、配置灵活能完全掌控在自己手里。自签名或Let‘s Encrypt证书用于保障“安全通道”和Web服务本身的通信加密。这套组合拳打下来既能享受内部部署的数据安全感又能获得类似云服务的远程访问便利性。2. 第一步基于Docker Compose的内部系统部署我们把“云容笔谈”系统看作一个由多个服务组成的应用。使用Docker Compose可以清晰地定义这些服务之间的关系一键启动整个环境。首先需要在公司的内部服务器比如一台Linux机器上安装Docker和Docker Compose。这个过程网上教程很多这里就不赘述了。接下来我们创建一个名为docker-compose.yml的配置文件。这个文件描述了我们要运行的服务。假设“云容笔谈”系统主要包含Web前端、AI模型推理后端和一个数据库。version: 3.8 services: # 数据库服务比如PostgreSQL用于存储用户信息和生成记录 database: image: postgres:15-alpine container_name: yunrong_db restart: unless-stopped environment: POSTGRES_DB: yunrong POSTGRES_USER: admin POSTGRES_PASSWORD: your_strong_password_here # 务必修改 volumes: - postgres_data:/var/lib/postgresql/data networks: - yunrong_network # AI模型推理后端服务 backend: image: your-registry/yunrong-backend:latest # 替换为实际的后端镜像 container_name: yunrong_backend restart: unless-stopped depends_on: - database environment: DATABASE_URL: postgresql://admin:your_strong_password_heredatabase:5432/yunrong MODEL_PATH: /app/models volumes: - model_data:/app/models # 挂载模型文件避免容器重建时丢失 - generated_images:/app/output # 挂载生成图片的存储目录 networks: - yunrong_network # Web前端服务 frontend: image: your-registry/yunrong-frontend:latest # 替换为实际的前端镜像 container_name: yunrong_frontend restart: unless-stopped depends_on: - backend environment: API_BASE_URL: http://backend:8000 # 前端通过容器网络访问后端 ports: - 127.0.0.1:3000:3000 # 只映射到本地回环地址暂不对外 networks: - yunrong_network # Nginx反向代理对外提供统一入口并处理HTTPS nginx: image: nginx:alpine container_name: yunrong_nginx restart: unless-stopped depends_on: - frontend ports: - 127.0.0.1:8443:443 # 监听本机443端口映射到容器443。也先不对外。 volumes: - ./nginx/conf.d:/etc/nginx/conf.d:ro # Nginx配置 - ./nginx/ssl:/etc/nginx/ssl:ro # SSL证书目录 - generated_images:/usr/share/nginx/html/generated:ro # 让Nginx能访问生成的图片 networks: - yunrong_network volumes: postgres_data: model_data: generated_images: networks: yunrong_network: driver: bridge配置文件关键点解读网络隔离所有服务都加入一个自定义的yunrong_network它们之间可以通过服务名如backend相互访问但与宿主机其他网络隔离。数据持久化使用volumes持久化数据库数据、模型文件和生成的图片确保容器重启后数据不丢失。安全映射frontend和nginx服务的ports映射都指定了127.0.0.1意味着它们只监听服务器本机的网络接口外部网络无法直接访问。这是内部部署安全性的第一道锁。依赖关系通过depends_on控制服务启动顺序确保数据库先就绪后端再启动最后是前端和Nginx。配置好之后在docker-compose.yml同级目录下执行一条命令整个系统就会在内部跑起来docker-compose up -d执行docker-compose ps可以查看所有服务状态看到都是Up就表示初步部署成功了。现在你可以在服务器本机通过https://localhost:8443来访问系统需要先配置Nginx和证书见下文但外部网络还完全摸不到边。3. 第二步配置Nginx与HTTPS加密虽然服务还没对外暴露但我们需要先把对内的服务入口整理好并加上HTTPS加密。这步是为后续的安全外访打基础。我们在与docker-compose.yml同级的目录下创建nginx/conf.d和nginx/ssl文件夹。1. 申请或生成SSL证书对于企业内网可以使用自签名证书但浏览器会有安全警告。更推荐为你的公网域名申请免费的Let‘s Encrypt证书然后将证书文件fullchain.pem和privkey.pem放入./nginx/ssl/目录。即使服务在内网通过内网穿透访问时使用有效的域名证书体验会好很多。2. 配置Nginx反向代理在./nginx/conf.d/下创建yunrong.conf文件server { listen 443 ssl http2; server_name your-internal-domain.local; # 这里可以是一个内部域名或直接填_ ssl_certificate /etc/nginx/ssl/fullchain.pem; ssl_certificate_key /etc/nginx/ssl/privkey.pem; # 安全增强的SSL配置可选但推荐 ssl_protocols TLSv1.2 TLSv1.3; ssl_ciphers HIGH:!aNULL:!MD5; ssl_prefer_server_ciphers on; # 前端静态文件 location / { proxy_pass http://frontend:3000; proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_set_header X-Forwarded-Proto $scheme; } # 后端API接口 location /api/ { proxy_pass http://backend:8000/; proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_set_header X-Forwarded-Proto $scheme; } # 静态资源如图片直接由Nginx服务 location /generated/ { alias /usr/share/nginx/html/generated/; expires 7d; add_header Cache-Control public, immutable; } # 可选的健康检查端点 location /health { access_log off; return 200 healthy\n; add_header Content-Type text/plain; } }这个配置告诉Nginx监听443端口启用HTTPS。将所有根路径请求转发给前端容器。将/api/开头的请求转发给后端容器。直接由Nginx高效地提供/generated/路径下的生成图片。修改配置后需要重启Nginx容器使其生效docker-compose restart nginx现在在内部服务器上你应该可以通过https://localhost:8443安全地访问到完整的“云容笔谈”系统了。4. 第三步实现安全的内网穿透访问这是最关键的一步我们要在内部服务和公网之间搭建一个加密隧道。我们选择frp来实现因为它允许我们在自己的云服务器上搭建服务端完全自主可控。架构原理在公网云服务器简称公网服务器上运行frps服务端。在企业内部服务器即运行Docker的服务器上运行frpc客户端。frpc主动连接到frps建立一个加密隧道。外部用户访问公网服务器的特定端口frps将流量通过隧道转发给内网的frpcfrpc再转发给内网的Nginx服务localhost:8443。具体操作1. 公网服务器端配置在公网服务器假设IP为1.2.3.4下载frp编辑frps.ini:[common] bind_port 7000 # frp服务端监听端口用于与客户端建立控制连接 token your_secure_token_here # 认证令牌增加安全性 # 仪表板可用于查看连接状态可选 dashboard_port 7500 dashboard_user admin dashboard_pwd your_dashboard_password启动服务端./frps -c ./frps.ini建议配置为系统服务如systemd使其常驻。2. 企业内部服务器端配置在内网服务器下载frp客户端编辑frpc.ini:[common] server_addr 1.2.3.4 # 你的公网服务器IP server_port 7000 token your_secure_token_here # 必须与服务端一致 [yunrong-web] # 自定义一个服务名称 type https # 因为我们的内部服务是HTTPS local_ip 127.0.0.1 local_port 8443 # 映射到本机的Nginx HTTPS端口 custom_domains ai.yourcompany.com # 你希望外部访问的域名 # 可选将内网服务的HTTP健康检查端口也暴露用于监控 [yunrong-health] type tcp local_ip 127.0.0.1 local_port 8443 remote_port 8444 # 公网服务器上的一个端口用于访问健康检查HTTP启动客户端./frpc -c ./frpc.ini同样建议配置为系统服务。3. 域名与防火墙配置将域名ai.yourcompany.com的DNS A记录指向你的公网服务器IP1.2.3.4。在公网服务器的防火墙中放行7000(frp控制端口)、443(HTTPS稍后配置) 以及7500(仪表板可选) 端口。4. 公网服务器Nginx配置最终入口现在外部流量到达公网服务器的443端口我们需要用公网服务器上的Nginx将请求代理到frp服务端监听的端口frps会将流量隧道转发。在公网服务器上配置Nginxserver { listen 443 ssl http2; server_name ai.yourcompany.com; ssl_certificate /path/to/your/public/cert/fullchain.pem; # 公网域名的证书 ssl_certificate_key /path/to/your/public/cert/privkey.pem; location / { # 关键代理到frps服务端。frps配置了vhost_http_port如8080来接收HTTP/HTTPS流量。 # 更常见的做法是frpc直接暴露一个公网端口如typetcp, remote_port443但这样证书需要在frp层面处理。 # 另一种更清晰的做法是frpc将内网8443端口以TCP方式映射到公网服务器的某个端口如10000然后公网Nginx代理到localhost:10000。 # 我们采用后一种方式修改frpc.ini # [yunrong-https-tcp] # type tcp # local_ip 127.0.0.1 # local_port 8443 # remote_port 10000 proxy_pass https://127.0.0.1:10000; # 指向frp映射的TCP端口 proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; proxy_set_header X-Forwarded-Proto $scheme; # 因为内网服务已经是HTTPS这里需要配置SSL验证可选根据内网证书情况 # proxy_ssl_verify off; } }对应的frpc.ini客户端配置调整为[yunrong-https-tcp] type tcp local_ip 127.0.0.1 local_port 8443 remote_port 10000重启公网服务器的Nginx和frp客户端。至此外部用户访问https://ai.yourcompany.com流量路径为用户 - 公网服务器Nginx(443) - 公网服务器frps(7000) - 隧道 - 内网frpc - 内网Nginx(8443) - Docker内部服务。数据全程在加密隧道和HTTPS中传输。5. 安全加固与运维建议方案搭起来了但企业级应用还得考虑安全和稳定。1. 访问控制frp令牌务必设置强令牌防止未授权连接。防火墙规则在公网服务器上严格限制仅允许必要的IP段访问7000(frp控制端口) 和443(业务端口)。例如只允许公司办公网络的IP。应用层认证在“云容笔谈”系统本身启用强密码策略、双因素认证并精细控制用户权限。2. 网络与传输安全全链路HTTPS从外到内都使用HTTPS包括内网穿透隧道frp支持TLS加密传输在[common]下配置tls_enable true。独立网络Docker Compose创建的独立网络隔离了应用与其他服务。定期更新及时更新Docker镜像、frp版本以及服务器系统修补安全漏洞。3. 监控与高可用日志收集集中收集Docker容器、Nginx和frp的日志便于排查问题。健康检查利用之前配置的/health端点或容器自带的健康检查配合监控系统如PrometheusGrafana进行监控。frp高可用对于核心业务可以考虑部署多个frp服务端和客户端实现负载均衡和故障转移。数据备份定期备份Docker卷中的数据postgres_data,model_data。4. 性能考量内网穿透会引入额外的网络延迟尤其是公网服务器与内网服务器之间的物理距离会影响速度。建议将公网服务器选在靠近主要外部用户或与内网服务器网络质量较好的区域。AI模型推理是计算密集型任务确保内部服务器有足够的GPU/CPU和内存资源。6. 总结回过头来看这套方案它确实解决了那个设计团队的核心痛点。数据留在了他们自己的机房心里踏实合作方通过一个固定的网址就能访问系统演示、协作都很方便。整个部署过程虽然涉及环节不少但每一步都有成熟的开源工具支持文档也丰富实际实施起来比预想的要顺利。这种基于Docker和内网穿透的混合架构其价值在于它提供了一种“鱼与熊掌兼得”的可能性。对于许多对数据敏感又有远程访问需求的中小企业或团队来说它可能比直接购买SaaS服务或搭建复杂的专线网络更具性价比和灵活性。当然没有完美的方案。这套架构的运维复杂度会比单纯的云服务高一些需要团队具备一定的Linux和网络知识。并且内网穿透的稳定性和速度依赖于那台公网服务器以及中间的网络链路这部分需要做好选型和监控。如果你正在规划类似系统的部署不妨从一个小型试点开始按照上述步骤搭建一个测试环境。先跑通流程验证稳定性和性能再逐步完善安全策略和监控体系。技术方案终究是工具找到最适合自己业务场景和团队能力的那个才是关键。获取更多AI镜像想探索更多AI镜像和应用场景访问 CSDN星图镜像广场提供丰富的预置镜像覆盖大模型推理、图像生成、视频生成、模型微调等多个领域支持一键部署。