You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何调整Docker Compose使容器化FastAPI连接本地Ubuntu的MariaDB

将容器化MariaDB迁移到本地Ubuntu主机的配置指南

步骤1:修改Docker Compose文件

直接移除原配置中的mariadb服务块,同时删除两个FastAPI服务里的depends_on: - mariadb项——现在数据库不在容器内,无需依赖容器启动顺序。

给每个FastAPI服务添加extra_hosts配置,对应docker run中的--add-host=host.docker.internal:host-gateway参数,让容器能访问本地主机。

修改后的完整Docker Compose如下:

version: '3'

services:
  traefik:
    image: traefik:v2.5
    network_mode: "host"
    container_name: traefik
    command:
      - "--api.insecure=true"
      - "--providers.docker=true"
      - "--entrypoints.websecure.address=:443" 
      - "--certificatesresolvers.myresolver.acme.tlschallenge=true"
      - "--certificatesresolvers.myresolver.acme.email=myemail@mydomain.com"
      - "--certificatesresolvers.myresolver.acme.storage=/letsencrypt/acme.json"
    volumes:
      - "./letsencrypt:/letsencrypt"
      - "/var/run/docker.sock:/var/run/docker.sock:ro"
    labels:
      - 'traefik.http.services.traefik.loadbalancer.server.port=443'
      
  fastapi-api1:
    build:
      context: ./API1/
      dockerfile: Dockerfile
    volumes:
      - "./files_user:/files"
    # 添加配置让容器访问本地主机
    extra_hosts:
      - "host.docker.internal:host-gateway"
    labels:
      - 'traefik.enable=true'
      - 'traefik.http.routers.fastapi-api1.rule=Host(`ap1.mydomain.com`) && PathPrefix(`/`)'
      - 'traefik.http.routers.fastapi-api1.entrypoints=websecure'
      - "traefik.http.routers.fastapi-api1.tls.certresolver=myresolver"
      - 'traefik.http.routers.fastapi-api1.tls=true'
      - 'traefik.http.services.fastapi-api1.loadbalancer.server.port=8000'
    container_name: fastapi-api1
    # 移除依赖容器的配置
    command: bash -c "uvicorn app.main:app --host 0.0.0.0 --port 8000 --timeout-keep-alive 240"
    restart: "on-failure:5"


  fastapi-api2:
    build:
      context: ./API2/
      dockerfile: Dockerfile
    volumes:
      - "./files:/files"
    # 添加配置让容器访问本地主机
    extra_hosts:
      - "host.docker.internal:host-gateway"
    labels:
      - 'traefik.enable=true'
      - 'traefik.http.routers.fastapi-api2.rule=Host(`api2.mydomain.com`) && PathPrefix(`/`)'
      - 'traefik.http.routers.fastapi-api2.entrypoints=websecure'
      - "traefik.http.routers.fastapi-api2.tls.certresolver=myresolver"
      - 'traefik.http.routers.fastapi-api2.tls=true'
      - 'traefik.http.services.fastapi-api2.loadbalancer.server.port=8001'
    container_name: fastapi-api2 
    # 移除依赖容器的配置
    command: bash -c "uvicorn app.main:app --host 0.0.0.0 --port 8001"
    restart: "on-failure:5"

步骤2:调整数据库连接配置

把环境变量DB_Container_Name的值改为host.docker.internal,FastAPI就能通过这个地址访问本地主机上的MariaDB。修改后的连接代码示例:

connection_url_api = URL.create(
    "mariadb+mariadbconnector",
    username=DB_Username_API,
    password=DB_Password_API,
    host=DB_Container_Name,  # 该变量值现在为"host.docker.internal"
    port=3306,
    database=DB_Name_For_Api_Tables,
    query=dict(charset="utf8mb4")
)

步骤3:配置本地MariaDB允许外部连接

默认MariaDB仅允许本地访问,需做以下修改:

  1. 编辑配置文件/etc/mysql/mariadb.conf.d/50-server.cnf,将bind-address改为0.0.0.0,保存后重启服务:sudo systemctl restart mariadb
  2. 创建允许容器访问的数据库用户(替换为你的实际信息):
CREATE USER 'api_user'@'%' IDENTIFIED BY 'your_password';
GRANT ALL PRIVILEGES ON your_api_db.* TO 'api_user'@'%';
FLUSH PRIVILEGES;

关于启动延迟(sleep 10)

本地MariaDB是常驻服务,无需等待容器启动,可直接删除sleep 10。若担心MariaDB偶尔重启导致连接失败,建议在FastAPI代码中添加数据库连接重试逻辑(比如SQLAlchemy的pool_pre_ping参数),比固定延迟更可靠。

内容的提问来源于stack exchange,提问作者Tom

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.03 17:07:21