Docker部署Golang项目和Mysql镜像
本文最后更新于:1 年前
前言
友情提示
本文学习需要了解一些Linux简单命令和Docker的一些命令
使用的项目我已经上传到github:https://github.com/Gopherlinzy/gin-gorm-example
一、获取一个可执行的项目
我自己写了一个简单的gin-gorm项目,github下载地址:https://github.com/Gopherlinzy/gin-gorm-example
1、拉取项目
打开Windows终端,输入命令:
1 |
|
2、配置
只需要拉取下来,修改 conf/app.ini 配置文件
1 |
|
二、编写Dockerfile文件
Dockerfile文件就是单纯的文件并没有文件后缀,我们来了解一下,Dockerfile的作用。
1 |
|
1、作用
- golang:latest 镜像为基础镜像,将工作目录设置为 $GOPATH/src/gin-gorm-example ,并将当前上下文目录的内容复制到 $GOPATH/src/gin-gorm-example 中。
- 在进行 go build 编译完毕后,将容器启动程序设置为 ./gin-gorm-example,也就是我们所编译的可执行文件。
- 注意:gin-gorm-example 在 docker 容器里编译,并没有在宿主机现场编译
2、说明
Dockerfile 文件是用于定义 Docker 镜像生成流程的配置文件,文件内容是一条条指令,每一条指令构建一层,因此每一条指令的内容,就是描述该层应当如何构建;这些指令应用于基础镜像并最终创建一个新的镜像
1)FROM
指定基础镜像(必须有的指令,并且必须是第一条指令)
2)WORKDIR
使用 WORKDIR 指令可以来指定工作目录(或者称为当前目录),以后各层的当前目录就被改为指定的目录,如果目录不存在,WORKDIR 会帮你建立目录
格式: WORKDIR <工作目录路径>
3)COPY
COPY 指令将从构建上下文目录中 <源路径> 的文件/目录复制到新的一层的镜像内的 <目标路径> 位置
1 |
|
4)RUN
用于执行命令行命令
格式:RUN <命令>
5)EXPOSE
EXPOSE 指令是声明运行时容器提供服务端口,这只是一个声明,在运行时并不会因为这个声明应用就会开启这个端口的服务
格式: EXPOSE <端口 1> [<端口 2>…]
在 Dockerfile 中写入这样的声明有两个好处
- 帮助镜像使用者理解这个镜像服务的守护端口,以方便配置映射
- 运行时使用随机端口映射时,也就是 docker run -P 时,会自动随机映射 EXPOSE 的端口
6)ENTRYPOINT
ENTRYPOINT 指令是指定容器启动程序及参数
ENTRYPOINT 的格式和 RUN 指令格式一样,分为两种格式
- exec 格式:
1 |
|
- shell 格式:
1 |
|
三、构建Docker镜像
gin-gorm-example 的项目根目录下执行 docker build -t gin-gorm-docker .
该命令作用是创建/构建镜像,-t 指定名称为 gin-gorm-docker,**.** 构建内容为当前上下文目录
四、验证镜像
查看所有的镜像,确定刚刚构建的 gin-gorm-docker 镜像是否存在
五、创建并运行一个新容器
执行命令 docker run -p 8080:8080 gin-gorm-docker
测试我们项目的API文档网址:http://localhost:8080/swagger/index.html
运行成功了么?
我们再测试一下用户登录这块,我在用户表自动创建这块自动插入了一条用户信息用户:admin和密码:123456,用我们的postman测试一下,测试网址:http://localhost:8080/auth?username=admin&password=123456。
我们仔细看看控制台的输出了一条错误
我们可以发现问题是在访问MySQL数据库的时候,连接数据库超时了!
这就是我们接下来要解决的问题
六、MySQL
1、拉取镜像
从 Docker 的公共仓库 Dockerhub 下载 MySQL 镜像(国内建议配个镜像),用pull指令拉取镜像,格式指令 docker pull 镜像名:版本号,不写版本号默认拉取最新版。
我们这里就用5.7版本的MySQL数据库就好了。
1 |
|
2、创建并运行一个MySQL容器
用run指令创建并运行容器
1 |
|
说明:
–name mysql:指定容器名称为mysql,方便查找和使用
-p xxxx:yyyy:宿主机上xxxx端口对应容器中yyyy端口,在外部访问时用的是宿主机上的端口
-e MYSQL_ROOT_PASSWORD=123456:给root用户设置默认密码为123456
-d:容器后台运行
mysql:镜像名称
3、连接数据库
我用的是Navicat连接MySQL。
初始化的 Mysql 应该如图
创建我们的blog数据库,后续测试需要
七、关联Golang项目和MySQL
1、删除原来的项目镜像
由于原本的镜像存在问题,我们需要修改Dockerfile文件里的数据库的地址,我们需要删除它,此处有几种做法
- 删除原本有问题的镜像,重新构建一个新镜像
- 重新构建一个不同 name、tag 的新镜像
删除原本的有问题的镜像,-f 是强制删除及其关联状态
若不执行 -f,你需要执行 docker ps -a 查到所关联的容器,将其 rm 解除两者依赖关系
1 |
|
2、修改配置文件
将项目的配置文件 conf/app.ini,内容修改为
1 |
|
3、重新构建镜像
重复先前的步骤,回到 gin-gorm 的项目根目录下执行
1 |
|
4、创建关联并运行一个新容器
我们如何将项目容器和MySQL容器创建关联?
在run指令内增加命令 –link mysql:mysql 让 Golang 容器与 Mysql 容器互联;通过 –link,可以在容器内直接使用其关联的容器别名进行访问,而不通过 IP,但是–link只能解决单机容器间的关联,在分布式多机的情况下,需要通过别的方式进行连接。
执行命令
1 |
|
MySQL容器的数据库也成功自动创建了三个数据表。
我们测试一下数据库是否已经关联,用户登录测试网址:http://localhost:8080/auth?username=admin&password=123456
大功告成!
八、持久化数据库
我们在每次启动一个 Mysql 容器时,数据库都是空的。另外容器删除之后,数据就丢失了。
我们学习了Docker Volume卷技术,了解了如何将数据生命周期独立于容器的生命周期之外,来更新一下我们的Mysql容器吧!
Docker Volume文章:https://blog.csdn.net/weixin_46618592/article/details/126591142?spm=1001.2014.3001.5501
1、数据卷
数据卷 是被设计用来持久化数据的,数据卷的生命周期独立于容器的生命周期,Docker 不会在容器被删除后自动删除 数据卷,并且也不存在垃圾回收这样的机制来处理没有任何容器引用的 数据卷。
数据卷 是一个可供一个或多个容器使用的特殊目录,它绕过 UFS,可以提供很多有用的特性:
- 数据卷可以在容器之间共享和重用。
- 对数据卷的修改会立马生效。
- 对数据卷的更新,不会影响镜像。
- 数据卷默认会一直存在,即使容器被删除。
注意:
数据卷的使用,类似于 Linux 下对目录或文件进行 mount,镜像中的被指定为挂载点的目录中的文件会隐藏掉,能显示看的是挂载的数据卷。
2、如何挂载?
- 首先创建一个目录用于存放数据卷;示例目录 E:/home/docker-mysql。
1 |
|
- 检查目录 E:/home/docker-mysql,多了很多数据库文件。
3、验证
- 新建一个blog数据库,并启动我们的gin-gorm-docker容器
- 用我们的token,去新增tags数据表的记录
http://localhost:8080/api/v1/tags?token=(登录后拿到的token)&name=linzy&state=1&created_by=linzy
4. 删除MySQL容器,在重新用镜像启动
1 |
|
验证完毕,你也可以操作一下:创建一些测试表和数据,然后删除当前容器,重新创建的容器,数据库数据也依然存在(当然了数据卷指向要一致)