docker 构建时遇到的问题

  • 执行docker build之后,显示can't load package: package .: no Go files in /go
  • 构建完毕后,在本地可以完美执行,但是在travis cli集成工作上构建后无法工作,报错:docker: Error response from daemon: invalid header field value "oci runtime error: container_linux.go:247: starting container process caused \"exec: \\\"./MathApp\\\": permission denied\"\n".

    问题的解决

    首先,我的项目结构如下:

MathApp
├── conf
│   └── app.conf
├── Dockerfile
├── main.go
├── main_test.go
└── views
    ├── invalid-route.html
    └── result.html

  一个简单的数学计算应用。通过访问网址,可以返回计算结果。更多内容请参考:如何使用Docker部署Go Web应用程序

显示can't load package: package .: no Go files in /go问题的原因及解决

  这是第一次构建镜像,我的Dockefile文件内容如下:

FROM golang:latest

# Create the directory where the application will reside
RUN mkdir /app

# build
RUN go build

# Copy the application files (needed for production)
ADD MathApp /app
ADD views /app/views
ADD conf /app/conf

# Set the working directory to the app directory
WORKDIR /app

# Expose the application on port 8080.
# This should be the same as in the app.conf file
EXPOSE 8080

# Set the entry point of the container to the application executable
ENTRYPOINT [ "./MathApp" ]

  由于构建的镜像体积比较到,所以我希望尽可能减小镜像的体积,所以就希望只将可执行文件及其执行时用到的资源文件加入到镜像中。为了免去麻烦,直接在Dockerfile文件中执行编译命令。然后,却报出了上面的错误。
  其中的原因只要和docker镜像的分层有关。docker构建过程中,每一个命令都在它的上一层镜像的环境中执行,而并不是在我们的项目环境下执行。也就是说,在我执行RUN go build命令时,它的运行环境应该是执行了RUN mkdir /app的镜像环境,此时镜像中并不包含main.go, main_test.go等代码文件,自然无法完成build任务。
  更多关于docker镜像分层的问题,请参考:浅析Docker镜像分层的注意事项_docker
  

docker构建的镜像运行时的权限问题

  修正第一次的问题后的Dockerfile文档如下(在构建docker镜像前进行编译):

FROM golang:latest

# Create the directory where the application will reside
RUN mkdir /app

# Copy the application files (needed for production)
ADD MathApp /app
ADD views /app/views
ADD conf /app/conf

# Set the working directory to the app directory
WORKDIR /app

# Expose the application on port 8080.
# This should be the same as in the app.conf file
EXPOSE 8080

# Set the entry point of the container to the application executable
ENTRYPOINT [ "./MathApp" ]

  这个在本地运行,完全没有问题。但是,无论是通过阿里云第三方构建而后拉倒本地运行,或者通过travis cli构建后运行测试,都会报错:

docker: Error response from daemon: invalid header field value "oci runtime error: container_linux.go:247: starting container process caused \"exec: \\\"./MathApp\\\": permission denied\"\n

  从错误的描述中可以看出,运行镜像时,没有执行入口文件MathApp的权限。那么,我们就在构建镜像时,赋予它这个权限,在添加入口文件的命令执行前,增加赋予权限的命令:

RUN chmod +x MathApp

  最终,修改后的Dockefile如下:

FROM golang:latest
# Create the directory where the application will reside
RUN mkdir /app

# Copy the application files (needed for production)
ADD MathApp /app
ADD views /app/views
ADD conf /app/conf

# Set the working directory to the app directory
WORKDIR /app

# Expose the application on port 8080.
# This should be the same as in the app.conf file
EXPOSE 8080

# give a permission
RUN chmod +x MathApp

# Set the entry point of the container to the application executable

ENTRYPOINT /app/MathApp
Logo

权威|前沿|技术|干货|国内首个API全生命周期开发者社区

更多推荐