docker部署教程G01 GO 实战web

1. 准备工作

  • 安装Docker Desktop:确保已经安装并启动了Docker Desktop。
  • 编写Dockerfile:在项目根目录下创建一个名为Dockerfile的文件。
  • 配置文件:确保你的配置文件(如docker-compose.yaml)中正确配置了MySQL的连接信息。

2. 编写Dockerfile(特别提示:我是提前编译好的goblog)

Dockerfile中定义如何构建和运行你的Go应用程序。以下是示例内容:

# 使用轻量级的alpine镜像作为运行环境
FROM alpine:latest

# 设置工作目录
WORKDIR /root/

# 复制编译好的可执行文件到容器中
COPY goblog .

# 复制.env文件到容器中
COPY .env .

# 暴露应用端口
EXPOSE 3000

# 运行应用程序
CMD ["./goblog"]
  1. 配置MySQL连接
    确保你的配置文件(如docker-compose.yaml)中正确配置了MySQL的连接信息。假设你的配置文件如下:

    services:
    app:
     build: .
     ports:
       - "3000:3000"
     environment:
       - APP_NAME=GoBlog
       - APP_ENV=local
       - APP_KEY=33446a9dcf9ea060a0a6532b166da32f304af0de
       - APP_DEBUG=true
       - APP_URL=http://localhost:3000
       - APP_LOG_LEVEL=debug
       - APP_PORT=3000
       - DB_CONNECTION=mysql
       - DB_HOST=db
       - DB_PORT=3306
       - DB_DATABASE=goblog
       - DB_USERNAME=root
       - DB_PASSWORD=root
       - SESSION_DRIVER=cookie
       - SESSION_NAME=goblog-session
     depends_on:
       - db
    
    db:
     image: mysql:5.7
     environment:
       - MYSQL_ROOT_PASSWORD=root
       - MYSQL_DATABASE=goblog
     ports:
       - "3306:3306"
     volumes:
       - db_data:/var/lib/mysql
    volumes:
    db_data:
  2. .env配置里修改如下

    DB_HOST=127.0.0.1改为DB_HOST=host.docker.internal

    注意:host.docker.internal是Docker提供的一个特殊DNS名称,用于从容器内部访问主机上的服务。

    5. 构建Docker镜像

打开命令行工具(如PowerShell或CMD),进入项目根目录,执行以下命令来构建Docker镜像:

docker build -t goblog .

6. 运行Docker容器

构建完成后,可以通过以下命令运行Docker容器:

docker run -d -p 8080:8080 --name goblog-container goblog

注意:goblog-container为容器名可以改为your-image-name
这会将主机的8080端口映射到容器内的8080端口,并以后台模式运行容器。

7. 验证部署

打开浏览器,访问http://localhost:8080,如果一切正常,你应该能看到你的Go应用程序正在运行。

注意事项

  • MySQL配置:确保MySQL服务器正在运行,并且允许从host.docker.internal进行连接。
  • 防火墙和安全组:确保防火墙或安全组没有阻止容器与主机之间的通信。
  • 日志查看:如果遇到问题,可以使用docker logs <container_id>命令查看容器的日志输出。

通过以上步骤,你应该能够在Windows系统上成功使用Docker部署goblog项目,并关联本地的MySQL数据库。

我在操作过程遇到的问题及的解决办法仅供参考

当Docker容器启动后立即退出并显示exited(1)时,通常表示容器内的应用程序在启动过程中遇到了错误。为了诊断问题,可以按照以下步骤进行排查和解决:

1. 查看容器日志

首先,查看容器的日志以获取详细的错误信息。使用以下命令查看日志:

docker logs goblog-container

这将输出容器启动时的日志信息,帮助你确定具体的问题所在。

  1. 检查配置文件
    确保.env文件中的配置信息正确无误,特别是数据库连接信息。
    确保MySQL服务器正在运行,并且允许从host.docker.internal进行连接。你可以通过以下命令检查MySQL是否可以正常访问:
    mysql -h host.docker.internal -u root -p
    输入密码后,如果能够成功连接到MySQL服务器,则说明配置正确。

    确保MySQL允许远程连接

确保MySQL服务器配置允许从host.docker.internal进行连接。你可以在MySQL配置文件(通常是my.cnfmy.ini)中添加或修改以下配置:

[mysqld]
bind-address = 0.0.0.0

然后重启MySQL服务。

检查防火墙设置

确保防火墙没有阻止端口 3306 的流量。你可以临时禁用防火墙进行测试,或者配置防火墙规则允许端口 3306 的流量。

示例:Windows 防火墙配置
打开“控制面板” -> “系统和安全” -> “Windows Defender 防火墙”。
点击“高级设置”。
在左侧选择“入站规则”,点击右侧的“新建规则”。
选择“端口”,点击“下一步”。
选择“TCP”,指定端口 3306,点击“下一步”。
选择“允许连接”,点击“下一步”。
根据需要选择适用的配置文件,点击“下一步”。
输入规则名称(例如“Allow MySQL Port 3306”),点击“完成”。

如果容器日志为空,这通常意味着应用程序在启动时没有输出任何日志信息,这可能是由于以下几个原因导致的:

  1. 应用程序没有正确加载配置文件:确保应用程序能够正确读取.env文件。
  2. 应用程序在启动时没有输出日志:检查应用程序的代码,确保在启动时有日志输出。
  3. 应用程序在启动时立即崩溃:应用程序可能在启动时遇到了未捕获的错误,导致没有输出日志。

1. 确认应用程序加载配置文件

确保你的应用程序能够正确加载.env文件。你可以在应用程序启动时添加一些日志输出,确认配置文件是否被正确加载。

示例代码修改

main.go中添加一些日志输出,确认配置文件是否被正确加载:

package main

import (
    "embed"
    "fmt"
    "goblog/app/http/middlewares"
    "goblog/bootstrap"
    "goblog/config"
    c "goblog/pkg/config"
    "log"
    "net/http"
)

//go:embed resources/views/articles/*
//go:embed resources/views/auth/*
//go:embed resources/views/categories/*
//go:embed resources/views/layouts/*
var tplFS embed.FS

//go:embed public/*
var staticFS embed.FS

func init() {
    // 初始化配置信息
    config.Initialize()
    // 输出配置信息以确认加载
    log.Printf("App Name: %s", c.GetString("app.name"))
    log.Printf("App Port: %s", c.GetString("app.port"))
    log.Printf("DB Host: %s", c.GetString("database.host"))
}

func main() {
    log.Println("Starting GoBlog application...")

    bootstrap.SetupDB()
    // 初始化模板
    bootstrap.SetupTemplate(tplFS)
    router := bootstrap.SetupRoute(staticFS)

    log.Printf("Listening on port %s...", c.GetString("app.port"))
    http.ListenAndServe(":"+c.GetString("app.port"), middlewares.RemoveTrailingSlash(router))
}

完。

本作品采用《CC 协议》,转载必须注明作者和本文链接
于江
讨论数量: 2

Dockerfile那一步,直接使用二阶段构建更合适,本地不要做构建。

1个月前 评论
heaker (楼主) 1个月前

讨论应以学习和精进为目的。请勿发布不友善或者负能量的内容,与人为善,比聪明更重要!