上一篇 下一篇 分享链接 返回 返回顶部

从零把 AI 聊天工具打包上线:Docker 部署实战与完整源码

发布人:慈云数据-客服中心 发布时间:9小时前 阅读量:3

AI工具 Docker部署教程|附源码

在 AI 应用快速发展的今天,越来越多开发者会把大模型能力集成到自己的工具、网站、后台系统或自动化流程中。例如:AI 聊天助手、文档总结工具、代码解释器、知识库问答机器人、图片生成助手等。

但是,很多 AI 工具在本地运行时会遇到一些常见问题:

  • 不同电脑环境不一致;
  • Python、Node.js 版本冲突;
  • 依赖包安装失败;
  • 部署到服务器后无法稳定运行;
  • 项目迁移困难;
  • 线上环境和本地环境不一致。

为了解决这些问题,Docker 是非常适合 AI 工具部署的一种方案。它可以把项目运行环境、依赖、配置统一打包成镜像,在任何支持 Docker 的机器上快速启动。

本文将以一个简单的 AI 聊天接口服务 为例,完整讲解如何使用 Docker 部署 AI 工具,并附上完整源码示例。


一、本文实现的 AI 工具功能

本文我们将实现一个简单的 AI 工具服务,主要包含以下功能:

  1. 提供一个 HTTP API 接口;
  2. 前端或其他系统可以通过接口提交问题;
  3. 后端调用 AI 模型接口;
  4. 返回 AI 生成的回答;
  5. 支持 Docker 镜像构建;
  6. 支持 Docker Compose 一键部署;
  7. 支持环境变量配置 API Key;
  8. 支持生产环境部署到服务器。

为了便于演示,本文使用 Python + FastAPI 开发后端服务。FastAPI 轻量、性能好、文档友好,非常适合 AI 工具类项目。

项目结构如下:

ai-tool-docker-demo/
├── app/
│   ├── main.py
│   └── ai_client.py
├── requirements.txt
├── Dockerfile
├── docker-compose.yml
├── .env.example
└── README.md

二、为什么 AI 工具适合用 Docker 部署?

AI 工具通常会涉及多种依赖,例如:

  • Python 运行环境;
  • AI SDK;
  • Web 框架;
  • 数据库;
  • 向量数据库;
  • 缓存服务;
  • 模型文件;
  • GPU 驱动;
  • 环境变量配置。

如果直接在服务器上手动安装,容易出现版本不兼容问题。比如本地 Python 是 3.11,服务器是 3.8;本地依赖包能安装,服务器安装时报错;本地运行正常,部署后接口异常。

Docker 的优势在于:

1. 环境一致

Docker 镜像中包含应用运行所需的环境、依赖和代码。只要镜像构建成功,在其他机器上运行时环境基本一致。

2. 部署简单

传统部署可能需要安装 Python、配置虚拟环境、安装依赖、启动进程管理器等。而 Docker 部署只需要:

docker compose up -d

即可启动服务。

3. 方便迁移

项目需要从一台服务器迁移到另一台服务器时,只需要复制代码或镜像,然后重新启动容器即可。

4. 易于扩展

如果 AI 工具访问量变大,可以通过多个容器实例进行扩展,也可以结合 Nginx、Kubernetes 等工具进行负载均衡。

5. 便于版本管理

每次发布可以构建不同版本的镜像,例如:

ai-tool:v1.0.0
ai-tool:v1.1.0
ai-tool:v2.0.0

出现问题时也可以快速回滚到旧版本。


三、准备工作

在开始之前,请确保你的电脑或服务器已经安装以下工具:

1. Docker

可以通过以下命令查看 Docker 是否安装成功:

docker -v

如果输出类似:

Docker version 26.1.0, build xxxxx

说明 Docker 已安装。

2. Docker Compose

新版 Docker 通常已经内置 Compose 插件,可以执行:

docker compose version

如果输出版本号,说明可用。

3. AI 模型 API Key

本文示例中会通过环境变量读取 API Key。你可以使用任意兼容的 AI 服务接口,例如 OpenAI、DeepSeek、通义千问、智谱、月之暗面等。

为了让源码更通用,示例代码采用标准 HTTP 请求方式调用模型接口,你可以根据实际平台调整接口地址和参数。


四、创建项目目录

首先创建项目目录:

mkdir ai-tool-docker-demo
cd ai-tool-docker-demo

创建子目录:

mkdir app

最终我们会在其中编写 Python 服务代码。


五、编写后端源码

1. 编写 requirements.txt

在项目根目录下创建 requirements.txt

fastapi==0.115.0
uvicorn[standard]==0.30.6
python-dotenv==1.0.1
requests==2.32.3

依赖说明:

  • fastapi:Web API 框架;
  • uvicorn:ASGI 服务,用于启动 FastAPI;
  • python-dotenv:用于本地读取 .env 配置;
  • requests:用于调用 AI 模型接口。

2. 编写 app/ai_client.py

app 目录下创建 ai_client.py

import os
import requests


class AIClient:
    def __init__(self):
        self.api_key = os.getenv("AI_API_KEY", "")
        self.api_base_url = os.getenv("AI_API_BASE_URL", "https://api.openai.com/v1/chat/completions")
        self.model = os.getenv("AI_MODEL", "gpt-4o-mini")

        if not self.api_key:
            print("Warning: AI_API_KEY is empty. Please set it in environment variables.")

    def chat(self, message: str) -> str:
        """
        调用 AI 模型接口,返回模型回复内容。
        这里使用通用 Chat Completions 格式,具体字段可根据服务商调整。
        """

        headers = {
            "Authorization": f"Bearer {self.api_key}",
            "Content-Type": "application/json"
        }

        payload = {
            "model": self.model,
            "messages": [
                {
                    "role": "system",
                    "content": "你是一个专业、简洁、友好的 AI 助手。"
                },
                {
                    "role": "user",
                    "content": message
                }
            ],
            "temperature": 0.7
        }

        try:
            response = requests.post(
                self.api_base_url,
                headers=headers,
                json=payload,
                timeout=60
            )

            response.raise_for_status()
            data = response.json()

            return data["choices"][0]["message"]["content"]

        except requests.exceptions.RequestException as e:
            return f"AI 接口请求失败:{str(e)}"
        except KeyError:
            return "AI 接口返回格式异常,请检查模型服务商返回数据结构。"

这段代码主要负责调用外部 AI 接口。它会读取以下环境变量:

AI_API_KEY
AI_API_BASE_URL
AI_MODEL

这样做的好处是代码不需要写死模型服务商信息,也避免了把 API Key 暴露在源码中。


3. 编写 app/main.py

继续创建 app/main.py

from fastapi import FastAPI
from pydantic import BaseModel
from app.ai_client import AIClient


app = FastAPI(
    title="AI Tool Docker Demo",
    description="一个使用 FastAPI + Docker 部署的 AI 工具示例",
    version="1.0.0"
)


class ChatRequest(BaseModel):
    message: str


class ChatResponse(BaseModel):
    reply: str


ai_client = AIClient()


@app.get("/")
def index():
    return {
        "name": "AI Tool Docker Demo",
        "version": "1.0.0",
        "status": "running"
    }


@app.get("/health")
def health_check():
    return {
        "status": "ok"
    }


@app.post("/chat", response_model=ChatResponse)
def chat(request: ChatRequest):
    reply = ai_client.chat(request.message)
    return ChatResponse(reply=reply)

这里定义了三个接口:

接口 方法 作用
/ GET 查看服务基本信息
/health GET 健康检查
/chat POST 调用 AI 聊天接口

其中 /chat 是核心接口。

请求示例:

{
  "message": "请用一句话介绍 Docker 的作用"
}

返回示例:

{
  "reply": "Docker 可以将应用及其依赖打包到容器中,从而实现快速、一致、可移植的部署。"
}

六、编写环境变量文件

在项目根目录创建 .env.example

AI_API_KEY=your_api_key_here
AI_API_BASE_URL=https://api.openai.com/v1/chat/completions
AI_MODEL=gpt-4o-mini
APP_PORT=8000

部署时复制一份:

cp .env.example .env

然后编辑 .env

AI_API_KEY=你的真实APIKey
AI_API_BASE_URL=你的模型接口地址
AI_MODEL=你的模型名称
APP_PORT=8000

注意:不要把真实 .env 文件提交到公开代码仓库。


七、编写 Dockerfile

在项目根目录创建 Dockerfile

FROM python:3.11-slim

WORKDIR /app

ENV PYTHONDONTWRITEBYTECODE=1
ENV PYTHONUNBUFFERED=1

COPY requirements.txt .

RUN pip install --no-cache-dir -r requirements.txt

COPY . .

EXPOSE 8000

CMD ["uvicorn", "app.main:app", "--host", "0.0.0.0", "--port", "8000"]

Dockerfile 说明

FROM python:3.11-slim

使用 Python 3.11 的精简镜像,体积较小,适合部署。

WORKDIR /app

设置容器内部工作目录为 /app

COPY requirements.txt .
RUN pip install --no-cache-dir -r requirements.txt

先复制依赖文件并安装依赖。这样做可以利用 Docker 缓存,只要依赖没有变化,后续构建会更快。

COPY . .

复制项目源码到容器中。

EXPOSE 8000

声明服务监听 8000 端口。

CMD [...]

容器启动后执行 FastAPI 服务。


八、编写 Docker Compose 配置

在项目根目录创建 docker-compose.yml

services:
  ai-tool:
    build:
      context: .
      dockerfile: Dockerfile
    container_name: ai-tool-demo
    ports:
      - "${APP_PORT:-8000}:8000"
    env_file:
      - .env
    restart: unless-stopped

配置说明:

  • build:表示从当前目录构建镜像;
  • container_name:容器名称;
  • ports:将宿主机端口映射到容器端口;
  • env_file:读取 .env 文件中的环境变量;
  • restart: unless-stopped:容器异常退出后自动重启。

九、本地运行测试

1. 复制环境变量文件

cp .env.example .env

修改 .env,填入真实 API Key。

2. 使用 Docker Compose 启动

docker compose up -d --build

参数说明:

  • up:启动服务;
  • -d:后台运行;
  • --build:启动前重新构建镜像。

3. 查看容器状态

docker ps

如果看到类似输出:

CONTAINER ID   IMAGE                         PORTS
xxxxxxx        ai-tool-docker-demo-ai-tool   0.0.0.0:8000->8000/tcp

说明服务启动成功。

4. 查看日志

docker logs -f ai-tool-demo

如果看到 Uvicorn 启动日志,表示接口服务正常运行。


十、接口测试

1. 测试首页接口

curl http://localhost:8000/

返回:

{
  "name": "AI Tool Docker Demo",
  "version": "1.0.0",
  "status": "running"
}

2. 测试健康检查接口

curl http://localhost:8000/health

返回:

{
  "status": "ok"
}

3. 测试 AI 聊天接口

curl -X POST http://localhost:8000/chat \
  -H "Content-Type: application/json" \
  -d '{"message":"请用通俗的话解释什么是容器化部署"}'

返回示例:

{
  "reply": "容器化部署就是把应用程序和它需要的运行环境一起打包起来,让它可以在不同服务器上以相同方式运行。"
}

十一、访问 FastAPI 自动文档

FastAPI 默认提供接口文档。启动服务后,可以在浏览器访问:

http://localhost:8000/docs

你会看到 Swagger UI 页面,可以直接在网页上测试 /chat 接口。

也可以访问:

http://localhost:8000/redoc

查看 ReDoc 风格的 API 文档。

这对于 AI 工具开发非常方便,尤其是在前后端联调时,可以快速确认接口字段和返回格式。


十二、服务器部署流程

如果要部署到云服务器,推荐流程如下。

1. 安装 Docker

以 Ubuntu 为例:

sudo apt update
sudo apt install -y docker.io docker-compose-plugin

启动 Docker:

sudo systemctl enable docker
sudo systemctl start docker

查看版本:

docker -v
docker compose version

2. 上传项目代码

可以使用 Git:

git clone https://你的仓库地址/ai-tool-docker-demo.git
cd ai-tool-docker-demo

也可以使用 scp 上传:

scp -r ai-tool-docker-demo root@服务器IP:/opt/

3. 配置环境变量

cp .env.example .env
vim .env

填入真实 API Key:

AI_API_KEY=sk-xxxxxxxx
AI_API_BASE_URL=https://api.openai.com/v1/chat/completions
AI_MODEL=gpt-4o-mini
APP_PORT=8000

4. 启动服务

docker compose up -d --build

5. 开放服务器端口

如果服务器有安全组,需要开放 8000 端口。
以云服务器控制台为例,需要添加入站规则:

协议:TCP
端口:8000
来源:你的IP 或 0.0.0.0/0

如果使用 Ubuntu 防火墙:

sudo ufw allow 8000

6. 访问服务

浏览器访问:

http://服务器IP:8000/docs

如果能看到接口文档,说明部署成功。


十三、添加 Nginx 反向代理

生产环境通常不建议直接暴露 8000 端口,而是使用 Nginx 反向代理到容器服务。

假设域名为:

ai.example.com

Nginx 配置示例:

server {
    listen 80;
    server_name ai.example.com;

    location / {
        proxy_pass http://127.0.0.1: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;
    }
}

保存后重载 Nginx:

sudo nginx -t
sudo systemctl reload nginx

如果需要 HTTPS,可以使用 Certbot 申请免费证书:

sudo apt install -y certbot python3-certbot-nginx
sudo certbot --nginx -d ai.example.com

配置完成后,就可以通过:

https://ai.example.com

访问 AI 工具服务。


十四、生产环境优化建议

1. 不要把 API Key 写进代码

API Key 应通过环境变量传入,例如 .env 文件、服务器环境变量、Kubernetes Secret 等。

错误示例:

api_key = "sk-xxxxxxx"

正确示例:

api_key = os.getenv("AI_API_KEY")

2. 增加请求鉴权

如果你的 AI 工具对外开放,建议增加接口鉴权,否则任何人都可以调用你的接口,造成费用损耗。

可以在请求头中增加一个 X-API-Token

import os
from fastapi import Header, HTTPException

APP_TOKEN = os.getenv("APP_TOKEN", "")

def verify_token(x_api_token: str = Header(default="")):
    if APP_TOKEN and x_api_token != APP_TOKEN:
        raise HTTPException(status_code=401, detail="Invalid token")

然后在接口中使用依赖校验。

3. 增加日志记录

建议记录以下信息:

  • 请求时间;
  • 请求 IP;
  • 请求接口;
  • 模型名称;
  • 响应耗时;
  • 异常信息。

但不要记录用户敏感数据和 API Key。

4. 设置超时时间

调用 AI 模型接口时一定要设置 timeout,避免请求长时间阻塞:

requests.post(url, json=payload, timeout=60)

5. 限流

如果接口公开访问,可以增加限流策略。例如:

  • 单 IP 每分钟最多请求 20 次;
  • 单用户每天最多调用 100 次;
  • 超过限制后返回 429。

6. 数据持久化

如果 AI 工具需要保存聊天记录、用户信息或任务记录,可以接入数据库:

  • PostgreSQL;
  • MySQL;
  • MongoDB;
  • Redis;
  • SQLite。

如果使用 Docker Compose,也可以把数据库作为另一个服务一起部署。


十五、常见问题排查

1. 容器启动失败

查看日志:

docker logs -f ai-tool-demo

常见原因:

  • Python 依赖安装失败;
  • 端口被占用;
  • .env 文件不存在;
  • 代码路径错误;
  • Dockerfile 中启动命令写错。

2. 访问不到接口

检查容器是否运行:

docker ps

检查端口映射:

docker compose ps

检查防火墙和云服务器安全组是否开放端口。

3. AI 接口返回 401

通常是 API Key 错误或没有权限。请检查:

AI_API_KEY=你的真实APIKey

同时确认服务商是否要求特定接口地址。

4. AI 接口返回格式异常

不同模型服务商返回格式可能略有不同。本文示例使用的是类似 OpenAI Chat Completions 的返回结构:

data["choices"][0]["message"]["content"]

如果你的服务商返回字段不同,需要修改 ai_client.py 中的解析逻辑。

5. Docker 构建速度慢

可以尝试配置镜像源,或者减少依赖体积。也可以使用更合理的 Dockerfile 缓存策略,例如先复制 requirements.txt 再复制源码。


十六、完整源码汇总

下面是本文项目的完整源码。

requirements.txt

fastapi==0.115.0
uvicorn[standard]==0.30.6
python-dotenv==1.0.1
requests==2.32.3

app/ai_client.py

import os
import requests


class AIClient:
    def __init__(self):
        self.api_key = os.getenv("AI_API_KEY", "")
        self.api_base_url = os.getenv("AI_API_BASE_URL", "https://api.openai.com/v1/chat/completions")
        self.model = os.getenv("AI_MODEL", "gpt-4o-mini")

        if not self.api_key:
            print("Warning: AI_API_KEY is empty. Please set it in environment variables.")

    def chat(self, message: str) -> str:
        headers = {
            "Authorization": f"Bearer {self.api_key}",
            "Content-Type": "application/json"
        }

        payload = {
            "model": self.model,
            "messages": [
                {
                    "role": "system",
                    "content": "你是一个专业、简洁、友好的 AI 助手。"
                },
                {
                    "role": "user",
                    "content": message
                }
            ],
            "temperature": 0.7
        }

        try:
            response = requests.post(
                self.api_base_url,
                headers=headers,
                json=payload,
                timeout=60
            )
            response.raise_for_status()
            data = response.json()
            return data["choices"][0]["message"]["content"]

        except requests.exceptions.RequestException as e:
            return f"AI 接口请求失败:{str(e)}"
        except KeyError:
            return "AI 接口返回格式异常,请检查模型服务商返回数据结构。"

app/main.py

from fastapi import FastAPI
from pydantic import BaseModel
from app.ai_client import AIClient


app = FastAPI(
    title="AI Tool Docker Demo",
    description="一个使用 FastAPI + Docker 部署的 AI 工具示例",
    version="1.0.0"
)


class ChatRequest(BaseModel):
    message: str


class ChatResponse(BaseModel):
    reply: str


ai_client = AIClient()


@app.get("/")
def index():
    return {
        "name": "AI Tool Docker Demo",
        "version": "1.0.0",
        "status": "running"
    }


@app.get("/health")
def health_check():
    return {
        "status": "ok"
    }


@app.post("/chat", response_model=ChatResponse)
def chat(request: ChatRequest):
    reply = ai_client.chat(request.message)
    return ChatResponse(reply=reply)

.env.example

AI_API_KEY=your_api_key_here
AI_API_BASE_URL=https://api.openai.com/v1/chat/completions
AI_MODEL=gpt-4o-mini
APP_PORT=8000

Dockerfile

FROM python:3.11-slim

WORKDIR /app

ENV PYTHONDONTWRITEBYTECODE=1
ENV PYTHONUNBUFFERED=1

COPY requirements.txt .

RUN pip install --no-cache-dir -r requirements.txt

COPY . .

EXPOSE 8000

CMD ["uvicorn", "app.main:app", "--host", "0.0.0.0", "--port", "8000"]

docker-compose.yml

services:
  ai-tool:
    build:
      context: .
      dockerfile: Dockerfile
    container_name: ai-tool-demo
    ports:
      - "${APP_PORT:-8000}:8000"
    env_file:
      - .env
    restart: unless-stopped

十七、总结

本文从零开始演示了一个 AI 工具的 Docker 部署流程,包括项目结构设计、FastAPI 接口开发、AI 接口调用、Dockerfile 编写、Docker Compose 一键启动、本地测试、服务器部署、Nginx 反向代理以及生产环境优化建议。

使用 Docker 部署 AI 工具的核心优势是:环境统一、部署简单、迁移方便、易于扩展、便于维护

如果你正在开发 AI 聊天助手、知识库问答、文档总结、代码生成、智能客服等工具,都可以参考本文的方式进行封装和部署。后续如果需要进一步增强,可以继续加入用户系统、数据库、向量检索、流式输出、接口鉴权、调用统计和费用控制等功能,让这个基础 AI 工具逐步演进为完整的生产级 AI 应用。

目录结构
全文