docker:go

Background

Provided that you are writing plans in Go and using the sync service sdk, docker:go is the builder you want to use. This builder produces plan artifacts which are usable on the local:docker or cluster:k8s runner.

Features

  • Produces docker containers which can run on docker-powered runners.
  • Linkage with a custom sync service SDK via --link-sdk flag
  • Simple command-line dependency mapping using the --dep flag
  • busybox base for easy container troubleshooting.
  • customizable build

Troubleshooting

Most build failures are caused by a problem with the plan code rather than the build process. Here are a few tips to help figure out what's going on when there are build failures.
  1. 1.
    Try to build the plan yourself. These are just executable files after all! Frequently, build problems can be revealed by simply trying to run the plan as it is. If you can't build it like this, then the builder won't be able to either.
    1
    cd <plan_directory>
    2
    export GOMOD111MODULE=on go build .
    Copied!
  2. 2.
    Make sure you have correctly initialized go.mod. The builder may throw errors when doing module replacements not used correctly.
  3. 3.
    Remove any custom module replace lines you have in go.mod. The builder will do this for you with appropriate flags.

Customizing the build

when using the docker:go builder, plans are build using a standard template. This template is typically all that is needed, but for some plans, the default docker build may be too inflexible. For cases such as this, the Dockerfile can be extended to include custom directives.
If you want to just provide your own Dockerfile, use the docker:generic builder instead.
This feature is best explained by showing how it works. This is the default Dockerfile the docker:go builder will use to build plans. Notice that this is a go template. The template has a few points where customizations can be added.
1
ARG BUILD_BASE_IMAGE
2
3
# This Dockerfile performs a multi-stage build and RUNTIME_IMAGE is the image
4
# onto which to copy the resulting binary.
5
#
6
# Picking a different runtime base image from the build image allows us to
7
# slim down the deployable considerably.
8
#
9
# The user can override the runtime image by passing in the appropriate builder
10
# configuration option.
11
ARG RUNTIME_IMAGE=busybox:1.31.1-glibc
12
13
#:::
14
#::: BUILD CONTAINER
15
#:::
16
FROM ${BUILD_BASE_IMAGE} AS builder
17
18
# PLAN_DIR is the location containing the plan source inside the container.
19
ENV PLAN_DIR /plan
20
21
# SDK_DIR is the location containing the (optional) sdk source inside the container.
22
ENV SDK_DIR /sdk
23
24
# Delete any prior artifacts, if this is a cached image.
25
RUN rm -rf ${PLAN_DIR} ${SDK_DIR} /testground_dep_list
26
27
# TESTPLAN_EXEC_PKG is the executable package of the testplan to build.
28
# The image will build that package only.
29
ARG TESTPLAN_EXEC_PKG="."
30
31
# GO_PROXY is the go proxy that will be used, or direct by default.
32
ARG GO_PROXY=direct
33
34
# BUILD_TAGS is either nothing, or when expanded, it expands to "-tags <comma-separated build tags>"
35
ARG BUILD_TAGS
36
37
# TESTPLAN_EXEC_PKG is the executable package within this test plan we want to build.
38
ENV TESTPLAN_EXEC_PKG ${TESTPLAN_EXEC_PKG}
39
40
# We explicitly set GOCACHE under the /go directory for more tidiness.
41
ENV GOCACHE /go/cache
42
43
{{.DockerfileExtensions.PreModDownload}}
44
45
# Copy only go.mod files and download deps, in order to leverage Docker caching.
46
COPY /plan/go.mod ${PLAN_DIR}/go.mod
47
48
{{if .WithSDK}}
49
COPY /sdk/go.mod /sdk/go.mod
50
{{end}}
51
52
# Download deps.
53
RUN echo "Using go proxy: ${GO_PROXY}" \
54
&& cd ${PLAN_DIR} \
55
&& go env -w GOPROXY="${GO_PROXY}" \
56
&& go mod download
57
58
{{.DockerfileExtensions.PostModDownload}}
59
60
{{.DockerfileExtensions.PreSourceCopy}}
61
62
# Now copy the rest of the source and run the build.
63
COPY . /
64
65
{{.DockerfileExtensions.PostSourceCopy}}
66
67
{{.DockerfileExtensions.PreBuild}}
68
69
RUN cd ${PLAN_DIR} \
70
&& go env -w GOPROXY="${GO_PROXY}" \
71
&& GOOS=linux GOARCH=amd64 go build -o ${PLAN_DIR}/testplan.bin ${BUILD_TAGS} ${TESTPLAN_EXEC_PKG}
72
73
{{.DockerfileExtensions.PostBuild}}
74
75
# Store module dependencies
76
RUN cd ${PLAN_DIR} \
77
&& go list -m all > /testground_dep_list
78
79
#:::
80
#::: (OPTIONAL) RUNTIME CONTAINER
81
#:::
82
83
{{ if not .SkipRuntimeImage }}
84
85
## The 'AS runtime' token is used to parse Docker stdout to extract the build image ID to cache.
86
FROM ${RUNTIME_IMAGE} AS runtime
87
88
# PLAN_DIR is the location containing the plan source inside the build container.
89
ENV PLAN_DIR /plan
90
91
{{.DockerfileExtensions.PreRuntimeCopy}}
92
93
COPY --from=builder /testground_dep_list /
94
COPY --from=builder ${PLAN_DIR}/testplan.bin /testplan
95
96
{{.DockerfileExtensions.PostRuntimeCopy}}
97
98
{{ else }}
99
100
## The 'AS runtime' token is used to parse Docker stdout to extract the build image ID to cache.
101
FROM builder AS runtime
102
103
# PLAN_DIR is the location containing the plan source inside the build container.
104
ENV PLAN_DIR /plan
105
106
RUN mv ${PLAN_DIR}/testplan.bin /testplan
107
108
{{ end }}
109
110
EXPOSE 6060
111
ENTRYPOINT [ "/testplan"]
Copied!
To add additional directives or customize your build further, add a section to your plan's manifest.toml. This example will add echo statements to each of the templated sections and turn off the runtime image:
1
[builders."docker:go"]
2
skip_runtime_image = true
3
4
[builders."docker:go".dockerfile_extensions]
5
pre_mod_download = "RUN echo 'at pre_mod_download'"
6
post_mod_download = "RUN echo 'at post_mod_download'"
7
pre_source_copy = "RUN echo 'at pre_source_copy'"
8
post_source_copy = "RUN echo 'at post_source_copy'"
9
pre_build = "RUN echo 'at pre_build'"
10
post_build = "RUN echo 'at post_build'"
11
pre_runtime_copy = "RUN echo 'at pre_runtime_copy'"
12
post_runtime_copy = "RUN echo 'at post_runtime_copy'"
Copied!
This example changes the build base image and enables the Go build cache:
1
[builders."docker:go"]
2
build_base_image = "golang:1.14.4-buster"
3
enable_go_build_cache = true
Copied!

Learn More

See an example plan which uses a customized Dockerfile, see here
Interested in how this works? All the Testground builders can be seen here
Last modified 1yr ago