skip to Main Content

I wanna make hot reloading for Golang on docker. I have created a Docker file looks like this:

# Go Version
FROM golang:latest

# Environment variables which CompileDaemon requires to run
ENV PROJECT_DIR=/app 
    GO111MODULE=on 
    CGO_ENABLED=0

# Basic setup of the container
RUN mkdir /app
COPY .. /app
WORKDIR /app

# Get CompileDaemon
RUN go get github.com/githubnemo/CompileDaemon
RUN go install github.com/githubnemo/CompileDaemon

# The build flag sets how to build after a change has been detected in the source code
# The command flag sets how to run the app after it has been built
ENTRYPOINT CompileDaemon -build="go build -o api" -command="./api"

and docker-compose.yml is:

version: '3.8'

name: live-reload-example

services:
  api:
    container_name: api
    build:
      context: .
      dockerfile: Dockerfile.dev
    ports:
      - 8501:8501
    volumes:
      - ./:/app

The container not reloading after the change

2

Answers


  1. Chosen as BEST ANSWER

    I used air package instead of CompileDaemon and problem solved.

    FROM golang:latest
    
    WORKDIR /go-app
    
    
    COPY go.mod go.sum ./
    RUN go mod download
    
    # Install the air binary so we get live code-reloading when we save files
    RUN curl -sSfL https://raw.githubusercontent.com/cosmtrek/air/master/install.sh | sh -s -- -b $(go env GOPATH)/bin
    
    
    CMD ["air", "-c", ".air.toml"]
    

    in the first step, the .air.toml file does not exist, and you must create it with air init in the docker container.


  2. Container should not be reloaded. It runs CompilerDaemon. The daemon watches the mounted files and recompiles+restarts the app upon change.

    I’m not sure about COPY .. /app – what’s there in ..? I replaced it with COPY . /app and it worked with my duppy app.

    Just a few points:

    • No need to create /app, WORKDIR creates it automatically,
    • No need to copy your app to /app upon build since go build is invoked after start, and the contents of /app is overloaded by the mounted volume

    Here is my Dockerfile

    FROM golang:latest
    
    # Environment variables which CompileDaemon requires to run
    ENV PROJECT_DIR=/app 
        GO111MODULE=on 
        CGO_ENABLED=0
    
    # Basic setup of the container
    WORKDIR /app
    # dummy module to make `go get` happy
    RUN go mod init dummy
    
    # Get CompileDaemon
    RUN go get github.com/githubnemo/CompileDaemon
    RUN go install github.com/githubnemo/CompileDaemon
    
    # The build flag sets how to build after a change has been detected in the source code
    # The command flag sets how to run the app after it has been built
    ENTRYPOINT CompileDaemon -build="go build -o api" -command="./api"
    

    Here is the log of docker compose up:

    api  | 2024/02/10 17:52:24 Running build command!
    api  | 2024/02/10 17:52:24 Build ok.
    api  | 2024/02/10 17:52:24 Restarting the given command.
    api  | 2024/02/10 17:52:24 stdout: Hello, world! Version 1
    api  | 2024/02/10 17:52:35 Running build command!
    api  | 2024/02/10 17:52:35 Build ok.
    api  | 2024/02/10 17:52:35 Hard stopping the current process..
    api  | 2024/02/10 17:52:35 Restarting the given command.
    api  | 2024/02/10 17:52:35 stdout: Hello, world! Version 2
    

    As you see, when the container started, it built my application and launched it. The output of the application:

    api  | 2024/02/10 17:52:24 stdout: Hello, world! Version 1
    

    Then I edited the app and changed the line to Version 2:

    api  | 2024/02/10 17:52:35 Running build command!
    api  | 2024/02/10 17:52:35 Build ok.
    api  | 2024/02/10 17:52:35 Hard stopping the current process..
    api  | 2024/02/10 17:52:35 Restarting the given command.
    api  | 2024/02/10 17:52:35 stdout: Hello, world! Version 2
    

    IMHO, the container works as expected: it watches changes in sources and rebuilds and restarts the application.

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search