From 5d534c08902b91105e272bcf3f703cf380d54d72 Mon Sep 17 00:00:00 2001 From: Shizun Ge Date: Fri, 24 Jul 2026 18:59:44 -0700 Subject: [PATCH 1/5] Rename enable_healthcheck flag to healthcheck_enable, reorder flags, and update README --- Dockerfile | 2 +- README.md | 10 ++-- main.go | 27 ++++++--- metrics/priority_queue_test.go | 102 +++++++++++++++++++++++++++++++++ 4 files changed, 127 insertions(+), 14 deletions(-) create mode 100644 metrics/priority_queue_test.go diff --git a/Dockerfile b/Dockerfile index 6450ecf..6fda926 100644 --- a/Dockerfile +++ b/Dockerfile @@ -19,4 +19,4 @@ HEALTHCHECK --interval=30s --timeout=3s --start-period=10s --retries=3 \ CMD ["/endlessh", "-healthcheck"] USER nobody ENTRYPOINT ["/endlessh"] -CMD ["-logtostderr", "-v=1", "-enable_healthcheck"] +CMD ["-logtostderr", "-v=1", "-healthcheck_enable"] diff --git a/README.md b/README.md index ec9907a..abd50a9 100644 --- a/README.md +++ b/README.md @@ -59,11 +59,13 @@ Usage of ./endlessh-go -geoip_supplier string Supplier to obtain Geohash of IPs. Possible values are "off", "ip-api", "max-mind-db" (default "off") -healthcheck - GET healthcheck_host:healthcheck_port/health and exit 1 if status is not ok or timeout is exceeded (for container healthcheck) + Perform healthcheck and exit. GET healthcheck_host:healthcheck_port/health and exit 1 if status is not ok or timeout is exceeded. + -healthcheck_enable + Enable healthcheck -healthcheck_host string - The address for container healthcheck (default "127.0.0.1") + The address for healthcheck. (default "127.0.0.1") -healthcheck_port string - HTTP port for container healthcheck; serves JSON with status and uptime at /health (default "51000") + HTTP port for healthcheck; Serves JSON with status and uptime at /health. (default "51000") -host string SSH listening address (default "0.0.0.0") -interval_ms int @@ -129,7 +131,7 @@ You could also use an offline GeoIP database from [MaxMind](https://www.maxmind. ## Healthcheck -The endlessh-go server exposes an HTTP health endpoint while the server is running. By default it listens on `127.0.0.1:51000` at `/health` and returns a JSON like this: +The endlessh-go server exposes an HTTP health endpoint when the `-healthcheck_enable` flag is set. By default it listens on `127.0.0.1:51000` at `/health` and returns a JSON like this: ```json { diff --git a/main.go b/main.go index 9392536..a1d51a6 100644 --- a/main.go +++ b/main.go @@ -131,25 +131,34 @@ const defaultPort = "2222" var connPorts arrayStrings func main() { + // Core SSH server flags + connHost := flag.String("host", "0.0.0.0", "SSH listening address") + flag.Var(&connPorts, "port", fmt.Sprintf("SSH listening port. You may provide multiple -port flags to listen to multiple ports. (default %q)", defaultPort)) + connType := flag.String("conn_type", "tcp", "Connection type. Possible values are tcp, tcp4, tcp6") intervalMs := flag.Int("interval_ms", 1000, "Message millisecond delay") bannerMaxLength := flag.Int64("line_length", 32, "Maximum banner line length") maxClients := flag.Int64("max_clients", 4096, "Maximum number of clients") - connType := flag.String("conn_type", "tcp", "Connection type. Possible values are tcp, tcp4, tcp6") - connHost := flag.String("host", "0.0.0.0", "SSH listening address") - flag.Var(&connPorts, "port", fmt.Sprintf("SSH listening port. You may provide multiple -port flags to listen to multiple ports. (default %q)", defaultPort)) + + // PROXY protocol flags + proxyProtocolEnabled := flag.Bool("proxy_protocol_enabled", false, "Enable PROXY protocol support. This causes the server to expect PROXY protocol headers on incoming connections.") + proxyProtocolReadHeaderTimeout := flag.Int("proxy_protocol_read_header_timeout_ms", 200, "Timeout for reading the PROXY protocol header in milliseconds. If the connection does not send a valid PROXY protocol header in this time, the header is ignored.") + + // Prometheus metrics flags prometheusEnabled := flag.Bool("enable_prometheus", false, "Enable prometheus") - healthcheckEnabled := flag.Bool("enable_healthcheck", false, "Enable healthcheck") prometheusHost := flag.String("prometheus_host", "0.0.0.0", "The address for prometheus") prometheusPort := flag.String("prometheus_port", "2112", "The port for prometheus") prometheusEntry := flag.String("prometheus_entry", "metrics", "Entry point for prometheus") prometheusCleanUnseenSeconds := flag.Int("prometheus_clean_unseen_seconds", 0, "Remove series if the IP is not seen for the given time. Set to 0 to disable. (default 0)") + + // GeoIP flags geoipSupplier := flag.String("geoip_supplier", "off", "Supplier to obtain Geohash of IPs. Possible values are \"off\", \"ip-api\", \"max-mind-db\"") maxMindDbFileName := flag.String("max_mind_db", "", "Path to the MaxMind DB file.") - proxyProtocolEnabled := flag.Bool("proxy_protocol_enabled", false, "Enable PROXY protocol support. This causes the server to expect PROXY protocol headers on incoming connections.") - proxyProtocolReadHeaderTimeout := flag.Int("proxy_protocol_read_header_timeout_ms", 200, "Timeout for reading the PROXY protocol header in milliseconds. If the connection does not send a valid PROXY protocol header in this time, the header is ignored.") - healthcheckHost := flag.String("healthcheck_host", health.DefaultHost, "The address for container healthcheck") - healthcheckPort := flag.String("healthcheck_port", health.DefaultPort, "HTTP port for container healthcheck; serves JSON with status and uptime at /health") - healthcheck := flag.Bool("healthcheck", false, "GET healthcheck_host:healthcheck_port/health and exit 1 if status is not ok or timeout is exceeded (for container healthcheck)") + + // Healthcheck flags + healthcheckEnabled := flag.Bool("healthcheck_enable", false, "Enable healthcheck") + healthcheckHost := flag.String("healthcheck_host", health.DefaultHost, "The address for healthcheck.") + healthcheckPort := flag.String("healthcheck_port", health.DefaultPort, "HTTP port for healthcheck; Serves JSON with status and uptime at /health.") + healthcheck := flag.Bool("healthcheck", false, "Perform healthcheck and exit. GET healthcheck_host:healthcheck_port/health and exit 1 if status is not ok or timeout is exceeded.") flag.Usage = func() { fmt.Fprintf(flag.CommandLine.Output(), "Usage of %v \n", os.Args[0]) diff --git a/metrics/priority_queue_test.go b/metrics/priority_queue_test.go new file mode 100644 index 0000000..74b189d --- /dev/null +++ b/metrics/priority_queue_test.go @@ -0,0 +1,102 @@ +package metrics + +import ( + "testing" + "time" +) + +func TestUpdatablePriorityQueue_PushAndPop(t *testing.T) { + pq := NewUpdatablePriorityQueue() + + now := time.Now() + pq.Update("item1", now.Add(2*time.Second)) + pq.Update("item2", now.Add(1*time.Second)) + pq.Update("item3", now.Add(3*time.Second)) + + if pq.pq.Len() != 3 { + t.Fatalf("Expected length 3, got %d", pq.pq.Len()) + } + + first := pq.Pop() + if first == nil { + t.Fatal("Pop returned nil") + } + if first.Key != "item2" { + t.Errorf("Expected first to be item2, got %s", first.Key) + } + + second := pq.Pop() + if second.Key != "item1" { + t.Errorf("Expected second to be item1, got %s", second.Key) + } + + third := pq.Pop() + if third.Key != "item3" { + t.Errorf("Expected third to be item3, got %s", third.Key) + } + + if pq.Pop() != nil { + t.Error("Expected pop on empty pq to return nil") + } +} + +func TestUpdatablePriorityQueue_UpdateExisting(t *testing.T) { + pq := NewUpdatablePriorityQueue() + + now := time.Now() + pq.Update("item1", now.Add(2*time.Second)) + pq.Update("item2", now.Add(3*time.Second)) + + // Update item2 to have an earlier time + pq.Update("item2", now.Add(1*time.Second)) + + first := pq.Peek() + if first == nil { + t.Fatal("Peek returned nil") + } + if first.Key != "item2" { + t.Errorf("Expected first to be item2 after update, got %s", first.Key) + } + + popFirst := pq.Pop() + if popFirst.Key != "item2" { + t.Errorf("Expected popped first to be item2, got %s", popFirst.Key) + } + + popSecond := pq.Pop() + if popSecond.Key != "item1" { + t.Errorf("Expected popped second to be item1, got %s", popSecond.Key) + } +} + +func TestUpdatablePriorityQueue_UpdateToLater(t *testing.T) { + pq := NewUpdatablePriorityQueue() + + now := time.Now() + pq.Update("item1", now.Add(1*time.Second)) + pq.Update("item2", now.Add(2*time.Second)) + + // Update item1 to have a later time than item2 + pq.Update("item1", now.Add(3*time.Second)) + + first := pq.Pop() + if first == nil || first.Key != "item2" { + t.Errorf("Expected first to be item2, got %v", first) + } + + second := pq.Pop() + if second == nil || second.Key != "item1" { + t.Errorf("Expected second to be item1, got %v", second) + } +} + +func TestUpdatablePriorityQueue_Empty(t *testing.T) { + pq := NewUpdatablePriorityQueue() + + if pq.Peek() != nil { + t.Error("Expected Peek on empty pq to return nil") + } + if pq.Pop() != nil { + t.Error("Expected Pop on empty pq to return nil") + } +} From 484c7fa79459673067c98d8aca9e431049349038 Mon Sep 17 00:00:00 2001 From: Shizun Ge Date: Fri, 24 Jul 2026 19:13:22 -0700 Subject: [PATCH 2/5] Add prometheus_enable flag and fallback from enable_prometheus --- README.md | 6 ++++-- examples/docker-simple/docker-compose.yml | 2 +- examples/kustomize-simple/deployment.yaml | 2 +- main.go | 18 +++++++++++++++--- 4 files changed, 21 insertions(+), 7 deletions(-) diff --git a/README.md b/README.md index abd50a9..555e68e 100644 --- a/README.md +++ b/README.md @@ -55,7 +55,7 @@ Usage of ./endlessh-go -conn_type string Connection type. Possible values are tcp, tcp4, tcp6 (default "tcp") -enable_prometheus - Enable prometheus + Enable prometheus (deprecated, use prometheus_enable) -geoip_supplier string Supplier to obtain Geohash of IPs. Possible values are "off", "ip-api", "max-mind-db" (default "off") -healthcheck @@ -90,6 +90,8 @@ Usage of ./endlessh-go SSH listening port. You may provide multiple -port flags to listen to multiple ports. (default "2222") -prometheus_clean_unseen_seconds int Remove series if the IP is not seen for the given time. Set to 0 to disable. (default 0) + -prometheus_enable + Enable prometheus -prometheus_entry string Entry point for prometheus (default "metrics") -prometheus_host string @@ -121,7 +123,7 @@ Endlessh-go exports the following Prometheus metrics. | endlessh_client_open_count | count | Number of connections of clients.
Labels:
| | endlessh_client_trapped_time_seconds | count | Seconds a client spends on endlessh.
Labels:
| -The metrics is off by default, you can turn it via the CLI argument `-enable_prometheus`. +The metrics is off by default, you can turn it via the CLI argument `-prometheus_enable`. It listens to port `2112` and entry point is `/metrics` by default. The port and entry point can be changed via CLI arguments. diff --git a/examples/docker-simple/docker-compose.yml b/examples/docker-simple/docker-compose.yml index 08ce471..17b997f 100644 --- a/examples/docker-simple/docker-compose.yml +++ b/examples/docker-simple/docker-compose.yml @@ -8,7 +8,7 @@ services: - -interval_ms=1000 - -logtostderr - -v=1 - - -enable_prometheus + - -prometheus_enable - -geoip_supplier=ip-api networks: - example_network diff --git a/examples/kustomize-simple/deployment.yaml b/examples/kustomize-simple/deployment.yaml index e7e7bc2..a8af852 100644 --- a/examples/kustomize-simple/deployment.yaml +++ b/examples/kustomize-simple/deployment.yaml @@ -14,7 +14,7 @@ spec: - -interval_ms=1000 - -logtostderr - -v=1 - - -enable_prometheus + - -prometheus_enable - -geoip_supplier=ip-api - -host=[::] - -prometheus_host=[::] diff --git a/main.go b/main.go index a1d51a6..8e2a4f7 100644 --- a/main.go +++ b/main.go @@ -144,7 +144,8 @@ func main() { proxyProtocolReadHeaderTimeout := flag.Int("proxy_protocol_read_header_timeout_ms", 200, "Timeout for reading the PROXY protocol header in milliseconds. If the connection does not send a valid PROXY protocol header in this time, the header is ignored.") // Prometheus metrics flags - prometheusEnabled := flag.Bool("enable_prometheus", false, "Enable prometheus") + prometheusEnabledOld := flag.Bool("enable_prometheus", false, "Enable prometheus (deprecated, use prometheus_enable)") + prometheusEnabledNew := flag.Bool("prometheus_enable", false, "Enable prometheus") prometheusHost := flag.String("prometheus_host", "0.0.0.0", "The address for prometheus") prometheusPort := flag.String("prometheus_port", "2112", "The port for prometheus") prometheusEntry := flag.String("prometheus_entry", "metrics", "Entry point for prometheus") @@ -173,7 +174,18 @@ func main() { os.Exit(0) } - if *prometheusEnabled { + prometheusEnabled := *prometheusEnabledNew + prometheusEnableSet := false + flag.Visit(func(f *flag.Flag) { + if f.Name == "prometheus_enable" { + prometheusEnableSet = true + } + }) + if !prometheusEnableSet { + prometheusEnabled = *prometheusEnabledOld + } + + if prometheusEnabled { if *connType == "tcp6" && *prometheusHost == "0.0.0.0" { *prometheusHost = "[::]" } @@ -189,7 +201,7 @@ func main() { metrics.InitPrometheus(*prometheusHost, *prometheusPort, *prometheusEntry) } - records := metrics.StartRecording(*maxClients, *prometheusEnabled, *prometheusCleanUnseenSeconds, + records := metrics.StartRecording(*maxClients, prometheusEnabled, *prometheusCleanUnseenSeconds, geoip.GeoOption{ GeoipSupplier: *geoipSupplier, MaxMindDbFileName: *maxMindDbFileName, From adc358371a8886d890158dfb2aaf36b904e128b1 Mon Sep 17 00:00:00 2001 From: Shizun Ge Date: Fri, 24 Jul 2026 19:18:53 -0700 Subject: [PATCH 3/5] Refactor healthcheck logic into SetupHealthcheck in health.go and add integration test --- endlessh_integration_test.go | 60 +++++++++++++++++++++++++++++++++++- health/health.go | 27 ++++++++++++++++ main.go | 22 +------------ 3 files changed, 87 insertions(+), 22 deletions(-) diff --git a/endlessh_integration_test.go b/endlessh_integration_test.go index c177c96..80f2cc4 100644 --- a/endlessh_integration_test.go +++ b/endlessh_integration_test.go @@ -263,7 +263,7 @@ func TestEndlesshIntegration_PrometheusMetrics(t *testing.T) { cmd := exec.Command( "go", "run", "main.go", "-port=0", - "-enable_prometheus", + "-prometheus_enable", "-prometheus_port=0", "-interval_ms=100", "-logtostderr", "-v=1", @@ -322,3 +322,61 @@ func TestEndlesshIntegration_PrometheusMetrics(t *testing.T) { t.Errorf("Expected bytes metric not found:\n%s", body) } } + +func TestEndlesshIntegration_Healthcheck(t *testing.T) { + var stderr bytes.Buffer + + cmd := exec.Command( + "go", "run", "main.go", + "-port=0", + "-healthcheck_enable", + "-healthcheck_port=0", + "-interval_ms=100", + "-logtostderr", "-v=1", + ) + cmd.Stderr = &stderr + + if err := cmd.Start(); err != nil { + t.Fatalf("Failed to start server: %v", err) + } + defer cmd.Process.Kill() + + if !waitForLogMatch(&stderr, "Starting healthcheck on http", waitForListenTimeout) { + t.Fatalf("Healthcheck listener did not start: %s", stderr.String()) + } + + reHealth := regexp.MustCompile(`Starting healthcheck on http://.*:(\d+)/health`) + healthMatch := reHealth.FindStringSubmatch(stderr.String()) + if len(healthMatch) < 2 { + t.Fatalf("Could not parse healthcheck port: %s", stderr.String()) + } + healthPort := healthMatch[1] + + // 1. Verify healthcheck HTTP endpoint returns valid JSON + resp, err := net.Dial("tcp", "localhost:"+healthPort) + if err != nil { + t.Fatalf("Failed to connect to healthcheck endpoint: %v", err) + } + fmt.Fprintf(resp, "GET /health HTTP/1.1\r\nHost: localhost\r\n\r\n") + + buf := make([]byte, 8192) + n, _ := resp.Read(buf) + body := string(buf[:n]) + resp.Close() + + if !strings.Contains(body, `"status":"ok"`) { + t.Errorf("Expected status:ok in health response: %s", body) + } + + // 2. Run the probe mode (-healthcheck) and verify it exits with 0 + probeCmd := exec.Command( + "go", "run", "main.go", + "-healthcheck", + "-healthcheck_port="+healthPort, + ) + var probeStderr bytes.Buffer + probeCmd.Stderr = &probeStderr + if err := probeCmd.Run(); err != nil { + t.Errorf("Healthcheck probe failed: %v, stderr: %s", err, probeStderr.String()) + } +} diff --git a/health/health.go b/health/health.go index 9843921..00420ec 100644 --- a/health/health.go +++ b/health/health.go @@ -21,6 +21,7 @@ import ( "net" "net/http" "os" + "strconv" "time" "github.com/golang/glog" @@ -84,3 +85,29 @@ func Probe(host, port string) bool { } return body.Status == "ok" } + +// SetupHealthcheck probes or starts the healthcheck listener as configured. +func SetupHealthcheck(healthcheck bool, healthcheckEnabled bool, connType string, healthcheckHost, healthcheckPort *string) { + if healthcheck { + if !Probe(*healthcheckHost, *healthcheckPort) { + os.Exit(1) + } + os.Exit(0) + } + + if healthcheckEnabled { + if connType == "tcp6" && *healthcheckHost == "0.0.0.0" { + *healthcheckHost = "[::]" + } + if *healthcheckPort == "0" || *healthcheckPort == "" { + l, err := net.Listen("tcp", *healthcheckHost+":0") + if err != nil { + glog.Fatalf("Failed to pick a free healthcheck port: %v", err) + } + actualPort := l.Addr().(*net.TCPAddr).Port + *healthcheckPort = strconv.Itoa(actualPort) + l.Close() + } + StartListener(*healthcheckHost, *healthcheckPort) + } +} diff --git a/main.go b/main.go index 8e2a4f7..1519b18 100644 --- a/main.go +++ b/main.go @@ -167,12 +167,7 @@ func main() { } flag.Parse() - if *healthcheck { - if !health.Probe(*healthcheckHost, *healthcheckPort) { - os.Exit(1) - } - os.Exit(0) - } + health.SetupHealthcheck(*healthcheck, *healthcheckEnabled, *connType, healthcheckHost, healthcheckPort) prometheusEnabled := *prometheusEnabledNew prometheusEnableSet := false @@ -208,21 +203,6 @@ func main() { }) clients := startSending(*maxClients, *bannerMaxLength, records) - if *healthcheckEnabled { - if *connType == "tcp6" && *healthcheckHost == "0.0.0.0" { - *healthcheckHost = "[::]" - } - if *healthcheckPort == "0" || *healthcheckPort == "" { - l, err := net.Listen("tcp", *healthcheckHost+":0") - if err != nil { - glog.Fatalf("Failed to pick a free healthcheck port: %v", err) - } - actualPort := l.Addr().(*net.TCPAddr).Port - *healthcheckPort = strconv.Itoa(actualPort) - l.Close() - } - health.StartListener(*healthcheckHost, *healthcheckPort) - } interval := time.Duration(*intervalMs) * time.Millisecond // Listen for incoming connections. From 9ca4057915140bd7eaa98f3dca10902cc1187cac Mon Sep 17 00:00:00 2001 From: Shizun Ge Date: Fri, 24 Jul 2026 19:24:57 -0700 Subject: [PATCH 4/5] Rename prometheus_enable and healthcheck_enable flags to prometheus_enabled and healthcheck_enabled --- Dockerfile | 2 +- README.md | 10 +++++----- endlessh_integration_test.go | 4 ++-- examples/docker-simple/docker-compose.yml | 2 +- examples/kustomize-simple/deployment.yaml | 2 +- main.go | 8 ++++---- 6 files changed, 14 insertions(+), 14 deletions(-) diff --git a/Dockerfile b/Dockerfile index 6fda926..767ca76 100644 --- a/Dockerfile +++ b/Dockerfile @@ -19,4 +19,4 @@ HEALTHCHECK --interval=30s --timeout=3s --start-period=10s --retries=3 \ CMD ["/endlessh", "-healthcheck"] USER nobody ENTRYPOINT ["/endlessh"] -CMD ["-logtostderr", "-v=1", "-healthcheck_enable"] +CMD ["-logtostderr", "-v=1", "-healthcheck_enabled"] diff --git a/README.md b/README.md index 555e68e..c25be9f 100644 --- a/README.md +++ b/README.md @@ -55,12 +55,12 @@ Usage of ./endlessh-go -conn_type string Connection type. Possible values are tcp, tcp4, tcp6 (default "tcp") -enable_prometheus - Enable prometheus (deprecated, use prometheus_enable) + Enable prometheus (deprecated, use prometheus_enabled) -geoip_supplier string Supplier to obtain Geohash of IPs. Possible values are "off", "ip-api", "max-mind-db" (default "off") -healthcheck Perform healthcheck and exit. GET healthcheck_host:healthcheck_port/health and exit 1 if status is not ok or timeout is exceeded. - -healthcheck_enable + -healthcheck_enabled Enable healthcheck -healthcheck_host string The address for healthcheck. (default "127.0.0.1") @@ -90,7 +90,7 @@ Usage of ./endlessh-go SSH listening port. You may provide multiple -port flags to listen to multiple ports. (default "2222") -prometheus_clean_unseen_seconds int Remove series if the IP is not seen for the given time. Set to 0 to disable. (default 0) - -prometheus_enable + -prometheus_enabled Enable prometheus -prometheus_entry string Entry point for prometheus (default "metrics") @@ -123,7 +123,7 @@ Endlessh-go exports the following Prometheus metrics. | endlessh_client_open_count | count | Number of connections of clients.
Labels:
  • `ip`: Remote IP of the client
  • `local_port`: Local port the program listens to
  • `country`: Country of the IP
  • `location`: Country, Region, and City
  • `geohash`: Geohash of the location
| | endlessh_client_trapped_time_seconds | count | Seconds a client spends on endlessh.
Labels:
  • `ip`: Remote IP of the client
  • `local_port`: Local port the program listens to
| -The metrics is off by default, you can turn it via the CLI argument `-prometheus_enable`. +The metrics is off by default, you can turn it via the CLI argument `-prometheus_enabled`. It listens to port `2112` and entry point is `/metrics` by default. The port and entry point can be changed via CLI arguments. @@ -133,7 +133,7 @@ You could also use an offline GeoIP database from [MaxMind](https://www.maxmind. ## Healthcheck -The endlessh-go server exposes an HTTP health endpoint when the `-healthcheck_enable` flag is set. By default it listens on `127.0.0.1:51000` at `/health` and returns a JSON like this: +The endlessh-go server exposes an HTTP health endpoint when the `-healthcheck_enabled` flag is set. By default it listens on `127.0.0.1:51000` at `/health` and returns a JSON like this: ```json { diff --git a/endlessh_integration_test.go b/endlessh_integration_test.go index 80f2cc4..11c703c 100644 --- a/endlessh_integration_test.go +++ b/endlessh_integration_test.go @@ -263,7 +263,7 @@ func TestEndlesshIntegration_PrometheusMetrics(t *testing.T) { cmd := exec.Command( "go", "run", "main.go", "-port=0", - "-prometheus_enable", + "-prometheus_enabled", "-prometheus_port=0", "-interval_ms=100", "-logtostderr", "-v=1", @@ -329,7 +329,7 @@ func TestEndlesshIntegration_Healthcheck(t *testing.T) { cmd := exec.Command( "go", "run", "main.go", "-port=0", - "-healthcheck_enable", + "-healthcheck_enabled", "-healthcheck_port=0", "-interval_ms=100", "-logtostderr", "-v=1", diff --git a/examples/docker-simple/docker-compose.yml b/examples/docker-simple/docker-compose.yml index 17b997f..ca32cc2 100644 --- a/examples/docker-simple/docker-compose.yml +++ b/examples/docker-simple/docker-compose.yml @@ -8,7 +8,7 @@ services: - -interval_ms=1000 - -logtostderr - -v=1 - - -prometheus_enable + - -prometheus_enabled - -geoip_supplier=ip-api networks: - example_network diff --git a/examples/kustomize-simple/deployment.yaml b/examples/kustomize-simple/deployment.yaml index a8af852..4eea0a1 100644 --- a/examples/kustomize-simple/deployment.yaml +++ b/examples/kustomize-simple/deployment.yaml @@ -14,7 +14,7 @@ spec: - -interval_ms=1000 - -logtostderr - -v=1 - - -prometheus_enable + - -prometheus_enabled - -geoip_supplier=ip-api - -host=[::] - -prometheus_host=[::] diff --git a/main.go b/main.go index 1519b18..581bf5d 100644 --- a/main.go +++ b/main.go @@ -144,8 +144,8 @@ func main() { proxyProtocolReadHeaderTimeout := flag.Int("proxy_protocol_read_header_timeout_ms", 200, "Timeout for reading the PROXY protocol header in milliseconds. If the connection does not send a valid PROXY protocol header in this time, the header is ignored.") // Prometheus metrics flags - prometheusEnabledOld := flag.Bool("enable_prometheus", false, "Enable prometheus (deprecated, use prometheus_enable)") - prometheusEnabledNew := flag.Bool("prometheus_enable", false, "Enable prometheus") + prometheusEnabledOld := flag.Bool("enable_prometheus", false, "Enable prometheus (deprecated, use prometheus_enabled)") + prometheusEnabledNew := flag.Bool("prometheus_enabled", false, "Enable prometheus") prometheusHost := flag.String("prometheus_host", "0.0.0.0", "The address for prometheus") prometheusPort := flag.String("prometheus_port", "2112", "The port for prometheus") prometheusEntry := flag.String("prometheus_entry", "metrics", "Entry point for prometheus") @@ -156,7 +156,7 @@ func main() { maxMindDbFileName := flag.String("max_mind_db", "", "Path to the MaxMind DB file.") // Healthcheck flags - healthcheckEnabled := flag.Bool("healthcheck_enable", false, "Enable healthcheck") + healthcheckEnabled := flag.Bool("healthcheck_enabled", false, "Enable healthcheck") healthcheckHost := flag.String("healthcheck_host", health.DefaultHost, "The address for healthcheck.") healthcheckPort := flag.String("healthcheck_port", health.DefaultPort, "HTTP port for healthcheck; Serves JSON with status and uptime at /health.") healthcheck := flag.Bool("healthcheck", false, "Perform healthcheck and exit. GET healthcheck_host:healthcheck_port/health and exit 1 if status is not ok or timeout is exceeded.") @@ -172,7 +172,7 @@ func main() { prometheusEnabled := *prometheusEnabledNew prometheusEnableSet := false flag.Visit(func(f *flag.Flag) { - if f.Name == "prometheus_enable" { + if f.Name == "prometheus_enabled" { prometheusEnableSet = true } }) From 47c7ed7b0655c9b0ac2bbe1cf6f3cfad6f11455e Mon Sep 17 00:00:00 2001 From: Shizun Ge Date: Fri, 24 Jul 2026 19:35:51 -0700 Subject: [PATCH 5/5] ci: ensure tests pass before building docker images in push and release workflows --- .github/workflows/on-pull-request.yml | 40 +-------------------------- .github/workflows/on-push.yml | 4 +-- .github/workflows/on-release.yml | 16 +++++++++++ 3 files changed, 18 insertions(+), 42 deletions(-) diff --git a/.github/workflows/on-pull-request.yml b/.github/workflows/on-pull-request.yml index ead7aab..4212d38 100644 --- a/.github/workflows/on-pull-request.yml +++ b/.github/workflows/on-pull-request.yml @@ -10,57 +10,19 @@ on: - 'README.md' - 'LICENSE' workflow_dispatch: - -env: - PLATFORMS: "linux/amd64,linux/arm64,linux/arm/v7" - + jobs: test: runs-on: ubuntu-latest steps: - name: Checkout code uses: actions/checkout@v7 - - name: Set up Go uses: actions/setup-go@v7 with: go-version: '1.26.1' cache: true - - name: Install dependencies run: go mod download - - name: Run Tests run: go test -v ./... - - build_container_image: - name: Build Docker image - runs-on: ubuntu-latest - steps: - - name: Checkout code - uses: actions/checkout@v7 - - name: Set up QEMU - uses: docker/setup-qemu-action@v4 - - name: Set up Docker Buildx - uses: docker/setup-buildx-action@v4.2.0 - - name: Docker meta - id: meta - uses: docker/metadata-action@v6 - with: - images: | - ghcr.io/${{ github.repository }}-development - tags: | - type=raw,value=dev-{{date 'X'}} - type=raw,value=latest - type=ref,event=branch - type=edge,branch=main - - name: Build - uses: docker/build-push-action@v7.3.0 - with: - platforms: ${{ env.PLATFORMS }} - push: false - tags: ${{ steps.meta.outputs.tags }} - labels: ${{ steps.meta.outputs.labels }} - provenance: false - - diff --git a/.github/workflows/on-push.yml b/.github/workflows/on-push.yml index c911a71..4b55747 100644 --- a/.github/workflows/on-push.yml +++ b/.github/workflows/on-push.yml @@ -21,21 +21,19 @@ jobs: steps: - name: Checkout code uses: actions/checkout@v7 - - name: Set up Go uses: actions/setup-go@v7 with: go-version: '1.26.1' cache: true - - name: Install dependencies run: go mod download - - name: Run Tests run: go test -v ./... build_and_push: name: Build and push Docker image runs-on: ubuntu-latest + needs: test if: ${{ github.actor != 'dependabot[bot]' }} steps: - name: Checkout code diff --git a/.github/workflows/on-release.yml b/.github/workflows/on-release.yml index dd7722c..025534c 100644 --- a/.github/workflows/on-release.yml +++ b/.github/workflows/on-release.yml @@ -8,9 +8,25 @@ env: PLATFORMS: "linux/amd64,linux/arm64,linux/arm/v7" jobs: + test: + runs-on: ubuntu-latest + steps: + - name: Checkout code + uses: actions/checkout@v7 + - name: Set up Go + uses: actions/setup-go@v7 + with: + go-version: '1.26.1' + cache: true + - name: Install dependencies + run: go mod download + - name: Run Tests + run: go test -v ./... + build_and_push: name: Build and push Docker image runs-on: ubuntu-latest + needs: test steps: - name: Checkout code uses: actions/checkout@v7