How to install Go in alpine linux
Solution 1
Thanks BMitch.
I compiled the go source code and performed the below steps inside alpine image container.
echo "installing go version 1.10.3..."
apk add --no-cache --virtual .build-deps bash gcc musl-dev openssl go
wget -O go.tgz https://dl.google.com/go/go1.10.3.src.tar.gz
tar -C /usr/local -xzf go.tgz
cd /usr/local/go/src/
./make.bash
export PATH="/usr/local/go/bin:$PATH"
export GOPATH=/opt/go/
export PATH=$PATH:$GOPATH/bin
apk del .build-deps
go version
Solution 2
I just copied it over using multi stage builds, seems to be ok so far
FROM XXX
COPY --from=golang:1.13-alpine /usr/local/go/ /usr/local/go/
ENV PATH="/usr/local/go/bin:${PATH}"
Solution 3
The following Dockerfile worked for me. Simpler and more abstract.
FROM alpine:latest
RUN apk add --no-cache git make musl-dev go
# Configure Go
ENV GOROOT /usr/lib/go
ENV GOPATH /go
ENV PATH /go/bin:$PATH
RUN mkdir -p ${GOPATH}/src ${GOPATH}/bin
# Install Glide
RUN go get -u github.com/Masterminds/glide/...
WORKDIR $GOPATH
CMD ["make"]
source: https://raw.githubusercontent.com/mickep76/alpine-golang/master/Dockerfile
Solution 4
With Alpine, you have libmusl instead of glibc. Alpine's libmusl is not a 1 for 1 replacement. Code linked against glibc will show a not found error which is actually from the dynamic linker. You can see what libraries are linked to the binary with ldd:
/ # ldd /usr/local/go/bin/go
/lib64/ld-linux-x86-64.so.2 (0x7f63ceed1000)
libpthread.so.0 => /lib64/ld-linux-x86-64.so.2 (0x7f63ceed1000)
libc.so.6 => /lib64/ld-linux-x86-64.so.2 (0x7f63ceed1000)
There are two options. The preferred option, and one used by docker's go images on Alpine, is to compile the go binaries on Alpine. You can see this in the Dockerfile for the golang image: https://github.com/docker-library/golang/blob/69f2d2a132565bf60afc91813801a3bdcc981526/1.10/alpine3.8/Dockerfile
The other option is to install glibc on Alpine, but once you start doing things like that, I'd question why use Alpine at all, and whether Debian or CentOS would be a more appropriate base image for you. Alpine has a wiki topic on this and there are third parties that have created glibc packages for alpine.
Solution 5
I found the best way to get golang
up running in alpine linux is to install it from source. This is also way followed in the official alpine go docker images.
FROM alpine:3.12
ARG GOLANG_VERSION=1.14.3
#we need the go version installed from apk to bootstrap the custom version built from source
RUN apk update && apk add go gcc bash musl-dev openssl-dev ca-certificates && update-ca-certificates
RUN wget https://dl.google.com/go/go$GOLANG_VERSION.src.tar.gz && tar -C /usr/local -xzf go$GOLANG_VERSION.src.tar.gz
RUN cd /usr/local/go/src && ./make.bash
ENV PATH=$PATH:/usr/local/go/bin
RUN rm go$GOLANG_VERSION.src.tar.gz
#we delete the apk installed version to avoid conflict
RUN apk del go
RUN go version
Yogesh Jilhawar
Updated on July 09, 2022Comments
-
Yogesh Jilhawar almost 2 years
I am trying to install Go inside an Alpine Docker image. For that I downloaded tar file from here inside my alpine docker image, untar it using following command:
tar -C /usr/local -xzf go1.10.3.linux-amd64.tar.gz
exported PATH to have go binary as:
export PATH=$PATH:/usr/local/go/bin
However, when I say
go version
then it says thatsh: go: not found
. I am quite new to alpine. Does anyone know, what I am missing here?Steps to reproduce-
$ docker run -it alpine sh $ wget https://dl.google.com/go/go1.10.3.linux-amd64.tar.gz $ tar -C /usr/local -xzf go1.10.3.linux-amd64.tar.gz $ export PATH=$PATH:/usr/local/go/bin $ go version
-
biolinh about 5 yearswhen you run "apk add --no-cache --virtual .build-deps bash gcc musl-dev openssl go ", you can run go version after that. Why do you need those lines between them ?
-
Yogesh Jilhawar about 5 yearsYou can do that also. However, I focused more on installing specific version of go
-
John Siu over 4 yearsYes, this should be the better answer.
-
Sean McCarthy over 3 years+1 Love this answer! I didn't realize one could combine two Docker images like that. Previously if I wanted two main programs in a container, I thought I had to get one FROM an image, and install the other one in a RUN command. Brilliant!
-
Davey over 2 yearsGreat answer. Looking at a current golang Dockerfile you can see the last few lines are related to the go path. If you need the go path then also include the following after the COPY in your Dockerfile
ENV GOPATH /go
ENV PATH $GOPATH/bin:$PATH
RUN mkdir -p "$GOPATH/src" "$GOPATH/bin" && chmod -R 777 "$GOPATH"
-
shellscape over 2 years
pkg
does not exist as a binary by default on Alpine