最近项目需要通过 k8s 部署,所以需要将我的go后端项目打包成docker镜像,运行在指定的环境内,于是记录一下自己第一次在mac上把go项目打包进 docker镜像
新建Dockerfile 文件,内容如下(这个是最重要的)
#源镜像
FROM golang:1.19-alpine3.16 as builder
#作者
MAINTAINER ic_xcc
RUN set -ex \
&& sed -i 's/dl-cdn.alpinelinux.org/mirrors.aliyun.com/g' /etc/apk/repositories \
&& apk --update add tzdata \
&& cp /usr/share/zoneinfo/Asia/Shanghai /etc/localtime \
&& apk --no-cache add ca-certificates
WORKDIR /build
# 创建了一个app-runner的用户, -D表示无密码
#RUN adduser -u 10001 -D app-runner
# 安装依赖包
ENV GOPROXY https://goproxy.cn
COPY go.mod .
COPY go.sum .
RUN go mod download
# 把当前目录的文件拷过去,编译代码
COPY . .
RUN CGO_ENABLED=0 GOARCH=amd64 GOOS=linux go build -a -ldflags '-w -s' -o blockchain-middleware .
# 暴露服务端口
EXPOSE 8088
FROM alpine:3.16 AS final
# 把构建结果、配置文件(有的话)和用户的相关文件拷过去
WORKDIR /app
COPY --from=builder /build/blockchain-middleware /app
COPY --from=builder /build/conf /app/conf
COPY --from=builder /build/config.toml /app
# 下载时区包
COPY --from=builder /usr/share/zoneinfo /usr/share/zoneinfo
# 设置当前时区
COPY --from=builder /usr/share/zoneinfo/Asia/Shanghai /etc/localtime
# https ssl证书
COPY --from=builder /etc/ssl/certs/ca-certificates.crt /etc/ssl/certs/
# 使用app-runner启动
#USER app-runner
ENTRYPOINT ["/app/blockchain-middleware"]
文中都配有注释,亲测打镜像有效
因我是mac电脑,所以我之前就有在电脑安装好docker环境,此时需要打开运行起我的docker
因为项目要求镜像仓库都上传到同一依赖地址,这个地址又是自己搭建的和互联网不同,只与办公网可链接的 ip 地址,所以提示了这个错误(这是因为我们docker client使用的是https,而我们搭建的Harbor私库用的是http的,所有会有这样的报错,导致访问不了),这个时候就需要修改一下 mac 上的 docker 配置了。
因 mac 上有图形化操作的 docker,于是依次从界面进入Preferences ->Docker Engine,将下面语句填写进去,也就是咱们使用的docker私库的地址
"insecure-registries":["仓库ip:port"]
如图所示:
配置完成后,点击右下角进行应用并且重启。
我们通过docker system info命令可以查看配置信息insecure-registries里是否有我们刚才配置的信息
现在就可以正常来连接远程docker库了。
在mac命令行中查看到我们写的 Dockerfile
构建项目程序镜像
docker build -f Dockerfile -t blockchain-middleware-docker-10:v1.3 .
docker images
会出现刚指定编译的镜像仓库和版本,镜像id、创建时间、大小等信息
说明
可以看到查看镜像后出现几个仓库名、标签都是的镜像,俗称:dangling image
产生原因:在编译镜像文件的时候存在一些编写错误,所以这些虚悬镜像可以删除掉他们
docker rmi $(docker images | grep "none" | awk '{print $3}')
使用docker run命令运行镜像
参数-d设置容器运行模式为后台运行。
参数-p 8088:80将容器内部使用的网络端口映射到主机上,其中8088为主机端口,80为容器内部使用端口。
# 运行镜像生成容器
docker run -d -p 8088:8088 -it --privileged=true blockchain-***:v1.3
# 查看所有容器
docker ps -a
运行后通过查看容器命令可看见容器STATUS状态为 up 启动模式
可选项说明
Options:
运行镜像生成容器后,可进入容器查看内部有些什么文件
# 容器进入(docker exec -it 容器id /bin/bash)-更改后的命令如下,原因见下详解
docker exec -it 54b0f2789ec5 /bin/sh
# 容器退出
exit
退出容器后,停止容器运行
docker stop 容器id
docker exec -it 容器id /bin/bash 想进入仓库查看配置,发现提示如下报错:OCI runtime exec failed: exec failed: container_linux.go:349: starting container process caused “exec: “/bin/bash”: stat /bin/bash: no such file or directory”: unknown
使用 docker exec -it 容器 id /bin/sh 或者
docker exec -it 容器 id sh
更改为docker exec -it cf34762e01c0 /bin/sh即可成功进入容器
当运行容器后,可以通过一些简单的接口调用尝试你的镜像是否可用,如下所示,镜像就可以正常使用拉。
完成以上步骤之后,说明你已经在本地打包好了一个可运行的镜像了
前提:默认你已经在阿里云创建好了对应的镜像仓库(若创建自己阿里云镜像仓库不行,可参考博文【阿里云-容器】Docker镜像管理快速入门)
我用阿里云镜像仓库举例子,当然公司是用我们自己搭建的镜像仓库,所以同理,根据你自身需求,登录相应镜像仓库即可(该登录操作在同环境下只需执行一次,会将你登录信息记录到相关环境配置文件内的,例如我电脑登录过一次我的阿里云镜像仓库后,后续拉取或推送都不用再登录后才能操作了)
# docker login --username=你的阿里云账号 阿里云镜像仓库
docker login --username=****ic registry.cn-hangzhou.aliyuncs.com
说明: 请将下面命令中的用户名替换为您的阿里云账号全名,回车后输入远程镜像仓库密码,密码为步骤六开通服务时设置的密码
docker tag [ImageId] registry.cn-hangzhou.aliyuncs.com/你阿里云自定义的命名空间/你阿里云自定义的镜像仓库名字:[镜像版本号]
例如:docker tag demo:v1 registry.cn-hangzhou.aliyuncs.com/space_test/demo:v1
docker push registry.cn-hangzhou.aliyuncs.com/你阿里云自定义的命名空间/你阿里云自定义的镜像仓库名字:[镜像版本号]
例如:docker push registry.cn-hangzhou.aliyuncs.com/space_test/demo:v1
如果你想从远程镜像中拉取指定版本到本地就使用如下命令,之后运行原理同上
docker pull registry.cn-hangzhou.aliyuncs.com/你阿里云自定义的命名空间/你阿里云自定义的镜像仓库名字:[镜像版本号]
例如:docker pull registry.cn-hangzhou.aliyuncs.com/space_test/demo:v1
除上述常用命令外,还有一些可能会使用到的 docker 命令有
镜像相关如下:
# 更改仓库名称或重命名镜像,例如:将名称更改test为 my_docker/test
docker image tag test:latest my_docker/test:latest
或
docker image tag fb583c3ac45d my_docker/test:latest
得到结果
REPOSITORY TAG IMAGE ID CREATED VIRTUAL SIZE
test latest fb583c3ac45d 35 minutes ago 968.5 MB
my_docker/test latest fb583c3ac45d 28 minutes ago 968.5 MB
tag 只是完整镜像名称(fb583c3ac45d…)的可读别名。因此,可以根据需要使它们与同一镜像关联。如果不喜欢旧名称,则可以在重新命名后将其删除
# 删除旧命令镜像,记得得到重新命名后的镜像
docker rmi test
容器相关如下:
# 启动容器
docker start cotianername/containerid
# 停止容器
docker stop cotianername/containerid
# 删除容器
docker rm cotianername/containerid
# 进入容器
docker exec -it containername/containerid /bin/bash
# 退出容器
exit
docker的虚悬镜像是什么
docker 如何删除none镜像
如何构建 Golang Dockerfiles
Golang Dockerfile的最佳实践
Golang项目通用Dockerfile编写
Docker部署GoLang程序,保姆级教程
Docker基础命令,镜像下载删除,容器显示,开启,关闭,杀死
docker镜像 容器 启动、停止、删除容器
如何给go项目打最小docker镜像,足足降低99%
构建包含jdk和nginx的基础镜像,部署前后端项目
Mac系统上 docker仓库提示 http: server gave HTTP response to HTTPS client 的解决方法