Ctrl K
ComunidadGuías…

main_status_launchd_test.go

Rama main · réplica de lectura del repositorio original.

Archivo original ↗Preguntar a KiBot
package main

import (
	"io"
	"log/slog"
	"net/http"
	"os"
	"runtime"
	"strings"
	"testing"
	"time"

	"github.com/kardianos/service"

	"github.com/pingular/pingularity/internal/config"
)

// These run against the launchd daemon `sudo pingularity install` put on THIS
// Mac, from an ordinary shell - the invocation the README shows. kardianos asks
// `launchctl list pingularity`, which answers for the caller's own domain: an
// unelevated caller looks in its login session, misses the system daemon, and
// the library turns the miss into "stopped" because the plist exists. Only
// Status() is ever called here (a read-only `launchctl list`); nothing starts,
// stops or loads the user's service. Skipped anywhere the setup is absent.
func liveLaunchdDaemon(t *testing.T) {
	t.Helper()
	if runtime.GOOS != "darwin" {
		t.Skip("launchd only")
	}
	if os.Geteuid() == 0 {
		t.Skip("root sees the system domain; the blind reading needs an ordinary user")
	}
	if _, err := os.Stat("/Library/LaunchDaemons/pingularity.plist"); err != nil {
		t.Skip("no installed launchd daemon on this Mac")
	}
	c := &http.Client{Timeout: 2 * time.Second}
	resp, err := c.Get("http://127.0.0.1:9000/healthz")
	if err != nil {
		t.Skipf("no daemon answering on :9000 to prove the service is alive: %v", err)
	}
	defer resp.Body.Close()
	body, _ := io.ReadAll(resp.Body)
	if resp.StatusCode != http.StatusOK || strings.TrimSpace(string(body)) != "ok" {
		t.Skipf("/healthz on :9000 did not answer ok (%d %q)", resp.StatusCode, body)
	}
}

// captureStatus runs `pingularity status` with os.Stdout pointed at a temp
// file and returns what it printed.
func captureStatus(t *testing.T) (string, error) {
	t.Helper()
	f, err := os.CreateTemp(t.TempDir(), "status")
	if err != nil {
		t.Fatalf("temp stdout: %v", err)
	}
	defer f.Close()
	orig := os.Stdout
	defer func() { os.Stdout = orig }()
	os.Stdout = f
	cmdErr := controlCmd("status", nil)
	b, err := os.ReadFile(f.Name())
	if err != nil {
		t.Fatalf("read captured status: %v", err)
	}
	return string(b), cmdErr
}

// A daemon answering /healthz is not "stopped". Unelevated on macOS the state
// cannot be read, and the command must say that - and where to look - rather
// than print a confident wrong answer with exit 0.
func TestStatusUnelevatedOnMacDoesNotCallALiveDaemonStopped(t *testing.T) {
	liveLaunchdDaemon(t)
	out, err := captureStatus(t)
	if err != nil {
		t.Fatalf("status returned an error: %v (output %q)", err, out)
	}
	if strings.Contains(out, "stopped") {
		t.Fatalf("status called a daemon that is answering /healthz stopped: %q", out)
	}
	if !strings.Contains(out, "sudo") || !strings.Contains(out, "healthz") {
		t.Errorf("status does not tell the operator how to learn the real state (sudo, or healthz): %q", out)
	}
}

// The same blind reading must not turn `restart` into `start`: that downgrade
// exists for a service KNOWN to be stopped, and here nothing is known.
func TestRestartIsNotDowngradedOnABlindLaunchdReading(t *testing.T) {
	liveLaunchdDaemon(t)
	prg := &program{cfg: config.Default(), log: slog.Default()}
	s, err := service.New(prg, svcConfig(nil))
	if err != nil {
		t.Fatalf("service.New: %v", err)
	}
	st, serr := s.Status()
	t.Logf("kardianos Status() from uid %d: %v, err=%v", os.Geteuid(), st, serr)
	if got := effectiveControlAction("restart", s); got != "restart" {
		t.Fatalf("restart downgraded to %q on a reading that cannot see the daemon", got)
	}
}