diff --git a/Dockerfile b/Dockerfile index 9a1a745449a7..a5b865c7f157 100644 --- a/Dockerfile +++ b/Dockerfile @@ -24,6 +24,9 @@ RUN ./scripts/build.sh # ============= Cleanup Stage ================ FROM debian:11-slim AS execution +# Install curl and jq to support healthchecks +RUN apt update && apt install -y curl jq + # Maintain compatibility with previous images RUN mkdir -p /avalanchego/build WORKDIR /avalanchego/build @@ -31,4 +34,7 @@ WORKDIR /avalanchego/build # Copy the executables into the container COPY --from=builder /build/build/ . +COPY scripts/docker/healthcheck.sh . +HEALTHCHECK --timeout=3s --start-period=1m CMD ./healthcheck.sh + CMD [ "./avalanchego" ] diff --git a/scripts/docker/docker-compose.yml b/scripts/docker/docker-compose.yml new file mode 100644 index 000000000000..6453871b2903 --- /dev/null +++ b/scripts/docker/docker-compose.yml @@ -0,0 +1,23 @@ +version: "3.3" +services: + autoheal: + image: willfarrell/autoheal:latest + container_name: autoheal + volumes: + - /var/run/docker.sock:/var/run/docker.sock + restart: unless-stopped + avalanchego: + image: avaplatform/avalanchego:latest + container_name: avalanchego + hostname: avalanchego + user: "9650" + labels: + autoheal: "true" + environment: + - HOME=/avalanchego + volumes: + - /home/avalanchego/.avalanchego:/avalanchego/.avalanchego + ports: + - 9650:9650 + - 9651:9651 + restart: unless-stopped diff --git a/scripts/docker/healthcheck.sh b/scripts/docker/healthcheck.sh new file mode 100755 index 000000000000..0770301a353c --- /dev/null +++ b/scripts/docker/healthcheck.sh @@ -0,0 +1,36 @@ +#!/bin/bash + +function isBootstrapped() { + # Check the Info API: + # https://docs.avax.network/apis/avalanchego/apis/info/#infoisbootstrapped + BOOTSTRAPPED=$(curl --silent -X POST --data '{ + "jsonrpc":"2.0", + "id" :1, + "method" :"info.isBootstrapped", + "params": { + "chain":"'"${1}"'" + } + }' -H 'content-type:application/json;' 127.0.0.1:9650/ext/info | jq .result.isBootstrapped) + + echo "${BOOTSTRAPPED}" +} + +# Check the Health API: +# https://docs.avax.network/apis/avalanchego/apis/health/ +HEALTHY=$(curl --silent -X POST --data '{ + "jsonrpc":"2.0", + "id" :1, + "method" :"health.health" +}' -H 'content-type:application/json;' 127.0.0.1:9650/ext/health | jq .result.healthy) +if [ "${HEALTHY}" = "true" ]; then + exit 0 +fi + +# Consider bootstrapping chains as healthy, even if the Health API says otherwise. +if [ "$(isBootstrapped 'P')" = "false" ] || \ + [ "$(isBootstrapped 'X')" = "false" ] || \ + [ "$(isBootstrapped 'C')" = "false" ]; then + exit 0 +fi + +exit 1