DokcerFile

DockerFile

构建一个简单的镜像

# 可以通过冒号添加引用
FROM alpine  
# 在哪个目录下工作           
WORKDIR /app   
# 把src下的文件,复制到 workdir 中 ,Add可以使用url   
COPY  src/ /app   
# 将echo复制到 1.txt下 # 构建的时候执行的脚本      
RUN echo 321 >>1.txt
# 启动起来以后运行的脚本,这个脚本运行完了,容器的整个生命周期也就结束了,所以一般这个都让他是一个阻塞的操作。   
CMD cat 1.txt 
docker build -t test01:v2 . #构建

docker run --rm aba         # 运行这个程序。

基础知识

  • 每个关键字都必须是大写字母

  • 执行顺序由上到下

  • # 表示注释

  • 每一个指令都会创建新的镜像层并提交

image

from # 基础镜像

MAINTAINER  # 已经弃用

label       # 名字+邮箱

run         # 镜像构建时候需要执行的命令

add         # 把这个压缩包添加到内容,也可以是 url

workdir     # 工作目录
volume      # 挂载的目录
expose      # 保留端口设置
cmd         # 容器启动时候要执行的命令
entrypoint  # 容器启动时候要执行的命令,可以追加命令
ONBUILD     # 当构建一个被继承dockerfile 这个时候就被会运行,触发指令
copy        # 类似于 ADD,将我们文件拷贝到镜像中,不支持解压
env         # 构建的时候设置环境变量

构建自己的ubuntu镜像

FROM ubuntu

LABEL name="depengzhao"

# ENV MyPath="/usr/local"

WORKDIR /usr/local



# 更换现在目录

RUN sed -i 's#http://archive.ubuntu.com/#http://mirrors.tuna.tsinghua.edu.cn/#' /etc/apt/sources.list;

RUN apt-get update && apt-get install -y vim

EXPOSE 80



CMD echo "Mypath"

CMD echo "-----end------"

CMD /bin/bash

运行更改后的镜像,就有 vim 命令了

image

通过history命令查看构造镜像的过程

image

使用 entrypoint 可以追加命令,这是他比 Run 命令高级的地方

docker run  -it  97 -l

cmd 和 entrypoint 区别

这两条指令,都是用来指定容器启动时运行的命令,故而大多功能都是重复的
具体可查看文章https://www.cnblogs.com/sparkdev/p/8461576.html

容器内的信号接收

docker killdokcer stop 命令,给容器发送信息时,只有进程为 1 的容器,可以接收到信号。

  • 使用 docker stop命令关闭容器时,会首先发送 SIGTERM信号,并等待其优雅关机,如果容器在指定的等待时间内(可以指定等待时间)没有结束,会再发送SIGKILL信号强制结束进程。
  • 使用 dcoekr kill命令时,默认发送 SIGKILL 信号,也可使用-s指定任意信号,例如
docker kill --signal="SIGTERM" my-app

exec 模式和 shell 模式

使用 exec模式时,容器中的任务进程就是容器内的 1 号进程,但由于exec这种方式,不会通过shell执行相关的命令,以此获取不到 $HOME这样的环境变量。

FROM ubuntu
CMD [ "top" ]

使用 shell模式时,docker会以 /bin/sh -c "task command" 的方式启动任务,因此容器内的 1号进程 不是任务进程而是 bash 进程。

FROM ubuntu
CMD top

cmd 和 entrypoint 区别

  • cmd: 容器启动时的命令行参数,可以覆盖 cmd 指定,并且只能覆盖,而不能追加参数
  • entrypoint: 容器启动时,可以追加参数,而不是被覆盖,当然显示指定 --entrypoint 进行覆盖。

使用 dockerfile 文件构建 go 程序

比如你想将如下文件打包成镜像

package main

import "fmt"

func main() {
	fmt.Println("你好,世界!")
}

使用 golang 为基础镜像构建

FROM golang:alpine
WORKDIR /build
COPY main.go .
RUN GOOS=linux go build -o hello main.go
CMD ["./hello"]

执行构建命令 docker build -t hello:V0.1 .

注意:

  1. 在构建镜像之前,先生成可运行的 hello 文件。在 linux 下可执行

  2. copy 命令可以用 add 代替并且功能更强大,add 可以直接解压并且支持 url

  3. run 在构建 docker 镜像时执行,cmd 在运行 docker 实例执行

  4. workdir 相当于 linux 的 cd 命令

使用基础镜像 alpine 构建

FROM alpine
WORKDIR /build
COPY main.go .
RUN GOOS=linux go build -o hello main.go
CMD ["./hello"]

构建镜像

docker build -t hello:V0.1  .

报错信息如下:

我个人以为,可能是因为 alpine 过于轻量级,所以没有 /shell 命令。

多阶段构建

FROM golang:alpine AS builder

WORKDIR /build

COPY . .
RUN GOOS=linux go build -o hello main.go


FROM alpine

WORKDIR /build
COPY --from=builder /build/hello /build/hello

CMD ["./hello"]

第一个 FROM 开始的部分是构建一个 builder 镜像,目的是在其中编译出可执行文件 hello,第二个 From 开始的部分是从第一个镜像里 copy 出来可执行文件 hello,并且用尽可能小的基础镜像 alpine 以保障最终镜像尽可能小,至于为啥不用更小的 scratch,是因为 scratch 真的啥也没有,有问题连上去看一眼的机会都没有,而 alpine 也才 5MB,对我们的服务不会构成多少影响。

使用gin 框架写的构建的demo

main函数

package main

import "github.com/gin-gonic/gin"

func main() {
	r := gin.Default()
	r.GET("/ping", func(c *gin.Context) {
		c.JSON(200, gin.H{
			"message": "pong",
		})
	})
	r.Run(":8080") // 监听并在 0.0.0.0:8080 上启动服务
}

Dockerfile 文件

FROM golang:alpine AS builder

WORKDIR /build

COPY . .
RUN GOPROXY=https://goproxy.cn GOOS=linux go build -o gindemo main.go


FROM alpine

WORKDIR /build
EXPOSE 8080
COPY --from=builder /build/gindemo /build/gindemo

CMD ["./gindemo"]

构建命令

docker  build -t gindemo:v1 .

其中 -t 是指定标签名字和版本的,特别注意最后的 . 不要忘记加。

Dokcer Compose

docker Compose 的含义,就是把多个的 docker打包到一起,用来一起管理和控制,详情请看官网 https://docs.docker.com/compose/gettingstarted/

查考文献

https://mp.weixin.qq.com/s/udpNP2LzF0bfn8w_wNcMYQ
https://www.cnblogs.com/sparkdev/p/8461576.html

posted @ 2021-07-06 21:57  沧海一声笑rush  阅读(53)  评论(0编辑  收藏  举报