diff --git a/alloy/config.alloy b/alloy/config.alloy index 9ac2aae7..8d4756d5 100644 --- a/alloy/config.alloy +++ b/alloy/config.alloy @@ -11,6 +11,17 @@ discovery.docker "docker_containers" { discovery.relabel "docker_logs" { targets = discovery.docker.docker_containers.targets + // discovery.docker sees every container on the host, not just this + // project's - keep only our own so multiple Eth Docker installs on one + // host don't ship each other's logs. Falls back to matching every + // container on the host if resolving COMPOSE_PROJECT_NAME ever fails, + // rather than matching none. + rule { + source_labels = ["__meta_docker_container_label_com_docker_compose_project"] + regex = coalesce(sys.env("COMPOSE_PROJECT_NAME"), ".*") + action = "keep" + } + rule { source_labels = ["__meta_docker_container_label_logs_collect"] regex = "true" @@ -37,6 +48,17 @@ loki.source.docker "docker_logs" { discovery.relabel "docker_metrics" { targets = discovery.docker.docker_containers.targets + // discovery.docker sees every container on the host, not just this + // project's - keep only our own so multiple Eth Docker installs on one + // host don't scrape/ship each other's metrics. Falls back to matching + // every container on the host if resolving COMPOSE_PROJECT_NAME ever + // fails, rather than matching none. + rule { + source_labels = ["__meta_docker_container_label_com_docker_compose_project"] + regex = coalesce(sys.env("COMPOSE_PROJECT_NAME"), ".*") + action = "keep" + } + rule { source_labels = ["__meta_docker_container_label_metrics_scrape"] regex = "true" diff --git a/ethd b/ethd index c6f724ab..61288670 100755 --- a/ethd +++ b/ethd @@ -2658,6 +2658,9 @@ reset to defaults." echo "Please make sure to run compatible client versions." fi + __pin_compose_project_name + __write_eth_docker_version_metric + if [[ ! "$OSTYPE" = "darwin"* ]]; then # Release lock and remove lock file exec 200<&- @@ -4281,13 +4284,74 @@ __adjust_grandine_permissions() { } +# Pins COMPOSE_PROJECT_NAME in .env to whatever Compose already resolves it +# to for this install, if it isn't already set there. This doesn't change +# which project Compose uses - the value is read back from Compose's own +# resolution (docker compose config), never computed independently - it just +# makes that name available for interpolation into the alloy container's +# environment (see grafana.yml), so config.alloy can scope Docker service +# discovery to this instance's own containers. Without this, Alloy's +# discovery.docker sees every container on the host's Docker socket, so +# running multiple Eth Docker installs on one host causes each instance's +# Alloy to also scrape/ship the others' metrics and logs. +__pin_compose_project_name() { + local existing + local resolved + + __get_value_from_env "COMPOSE_PROJECT_NAME" "${__env_file}" "existing" + if [[ -n "${existing}" ]]; then + return 0 + fi + + resolved=$(__docompose config 2>/dev/null | awk -F': ' '/^name:/{print $2; exit}') || resolved="" + if [[ -z "${resolved}" ]]; then + return 0 + fi + + __update_value_in_env "COMPOSE_PROJECT_NAME" "${resolved}" "${__env_file}" +} + + +# Writes the currently checked-out Eth Docker version as a node-exporter +# textfile-collector metric (see grafana.yml), so it can be tracked the same +# way the EL/CL client versions already are. "tag" comes from README.md's +# "This is Eth Docker vX.Y.Z" line (the same source `version` reads). A +# release commit bumps that line straight to "vX.Y.Z-dev" for the next +# version, so this stays accurate on main between releases. Writes into +# the same host directory node-exporter's textfile collector is already +# mounted from (NODE_EXPORTER_COLLECTOR_MOUNT_PATH, defaulting to +# ./.eth/node-exporter-text) - that mount is read-only inside the +# container, so the file has to land there from the host side. +__write_eth_docker_version_metric() { + local tag + local commit + local textfile_dir + + tag=$(grep -m1 "^This is Eth Docker v" README.md 2>/dev/null | sed -E 's/^This is Eth Docker //') || tag="" + commit=$(${__as_owner} git rev-parse --short HEAD 2>/dev/null) || commit="" + + __get_value_from_env "NODE_EXPORTER_COLLECTOR_MOUNT_PATH" "${__env_file}" "textfile_dir" + textfile_dir="${textfile_dir:-./.eth/node-exporter-text}" + + ${__as_owner} mkdir -p "${textfile_dir}" + { + echo "# HELP eth_docker_version_info Currently checked out Eth Docker version" + echo "# TYPE eth_docker_version_info gauge" + echo "eth_docker_version_info{tag=\"${tag}\",commit=\"${commit}\"} 1" + } | ${__as_owner} tee "${textfile_dir}/eth-docker-version.prom.tmp" >/dev/null + ${__as_owner} mv "${textfile_dir}/eth-docker-version.prom.tmp" "${textfile_dir}/eth-docker-version.prom" +} + + upgrade() { update } start() { + __pin_compose_project_name __adjust_grandine_permissions + __write_eth_docker_version_metric __docompose up -d --remove-orphans "$@" } diff --git a/grafana-cloud.yml b/grafana-cloud.yml index 71f0f680..34ba4849 100644 --- a/grafana-cloud.yml +++ b/grafana-cloud.yml @@ -52,7 +52,7 @@ services: - /sys:/host/sys:ro,rslave - /etc/hostname:/etc/nodename:ro - /etc/localtime:/etc/localtime:ro - - ${NODE_EXPORTER_COLLECTOR_MOUNT_PATH:-/tmp/dummy-nodeexp-text}:/tmp/text-collector:ro + - ${NODE_EXPORTER_COLLECTOR_MOUNT_PATH:-./.eth/node-exporter-text}:/tmp/text-collector:ro <<: *logging labels: - metrics.scrape=true @@ -120,6 +120,8 @@ services: alloy: image: grafana/alloy:latest restart: unless-stopped + environment: + - COMPOSE_PROJECT_NAME=${COMPOSE_PROJECT_NAME} volumes: - alloy-data:/var/lib/alloy - ./alloy:/etc/alloy diff --git a/grafana-rootless.yml b/grafana-rootless.yml index 86ed5911..d0d9410f 100644 --- a/grafana-rootless.yml +++ b/grafana-rootless.yml @@ -94,6 +94,8 @@ services: alloy: image: grafana/alloy:latest restart: unless-stopped + environment: + - COMPOSE_PROJECT_NAME=${COMPOSE_PROJECT_NAME} volumes: - alloy-data:/var/lib/alloy - ./alloy:/etc/alloy diff --git a/grafana.yml b/grafana.yml index 39d9ba1d..e2377dd4 100644 --- a/grafana.yml +++ b/grafana.yml @@ -75,7 +75,7 @@ services: - /sys:/host/sys:ro,rslave - /etc/hostname:/etc/nodename:ro - /etc/localtime:/etc/localtime:ro - - ${NODE_EXPORTER_COLLECTOR_MOUNT_PATH:-/tmp/dummy-nodeexp-text}:/tmp/text-collector:ro + - ${NODE_EXPORTER_COLLECTOR_MOUNT_PATH:-./.eth/node-exporter-text}:/tmp/text-collector:ro command: - '--path.rootfs=/rootfs' - '--path.sysfs=/host/sys' @@ -151,6 +151,8 @@ services: alloy: image: grafana/alloy:latest restart: unless-stopped + environment: + - COMPOSE_PROJECT_NAME=${COMPOSE_PROJECT_NAME} volumes: - alloy-data:/var/lib/alloy - ./alloy:/etc/alloy