ananke/testing/state/state_quality_branch_closeout_test.go

142 lines
5.0 KiB
Go

package statequality
import (
"os"
"path/filepath"
"strings"
"testing"
"time"
"scm.bstein.dev/bstein/ananke/internal/state"
)
// TestStateEnsureDirAndWriteIntentBranchCoverage runs one orchestration or CLI step.
// Signature: TestStateEnsureDirAndWriteIntentBranchCoverage(t *testing.T).
// Why: closes remaining success-branch gaps in EnsureDir and WriteIntent timestamp preservation.
func TestStateEnsureDirAndWriteIntentBranchCoverage(t *testing.T) {
root := t.TempDir()
dir := filepath.Join(root, "state")
if err := state.EnsureDir(dir); err != nil {
t.Fatalf("EnsureDir success path failed: %v", err)
}
if stat, err := os.Stat(dir); err != nil || !stat.IsDir() {
t.Fatalf("expected ensured state dir to exist, stat err=%v", err)
}
intentPath := filepath.Join(dir, "intent.json")
ts := time.Now().UTC().Add(-time.Minute).Truncate(time.Second)
if err := state.WriteIntent(intentPath, state.Intent{
State: state.IntentNormal,
Reason: "preserve-updated-at",
Source: "test",
UpdatedAt: ts,
}); err != nil {
t.Fatalf("WriteIntent with explicit UpdatedAt failed: %v", err)
}
got, err := state.ReadIntent(intentPath)
if err != nil {
t.Fatalf("ReadIntent after explicit UpdatedAt write failed: %v", err)
}
if !got.UpdatedAt.Equal(ts) {
t.Fatalf("expected UpdatedAt to remain unchanged; got=%s want=%s", got.UpdatedAt, ts)
}
}
// TestStateStoreLockAndLoadBranchCoverage runs one orchestration or CLI step.
// Signature: TestStateStoreLockAndLoadBranchCoverage(t *testing.T).
// Why: closes remaining lock/load branch gaps used by daemon and CLI quality gates.
func TestStateStoreLockAndLoadBranchCoverage(t *testing.T) {
root := t.TempDir()
lockPath := filepath.Join(root, "ananke.lock")
unlock, err := state.AcquireLock(lockPath)
if err != nil {
t.Fatalf("AcquireLock fresh lock failed: %v", err)
}
unlock()
storePath := filepath.Join(root, "runs.json")
if err := os.WriteFile(storePath, []byte{}, 0o640); err != nil {
t.Fatalf("write empty store file: %v", err)
}
recs, err := state.New(storePath).Load()
if err != nil {
t.Fatalf("Load empty store file failed: %v", err)
}
if len(recs) != 0 {
t.Fatalf("expected zero records from empty store file, got %d", len(recs))
}
}
// TestStateIntentParserAdditionalEdges runs one orchestration or CLI step.
// Signature: TestStateIntentParserAdditionalEdges(t *testing.T).
// Why: covers parser edge branches where source and updated_at tokens are absent/blank.
func TestStateIntentParserAdditionalEdges(t *testing.T) {
afterBlank, err := state.ParseIntentOutput("\nintent=normal source=peer")
if err != nil {
t.Fatalf("ParseIntentOutput with leading blank line failed: %v", err)
}
if afterBlank.State != state.IntentNormal {
t.Fatalf("unexpected parsed state after blank line: %+v", afterBlank)
}
in, err := state.ParseIntentOutput("intent=normal source=peer updated_at=")
if err != nil {
t.Fatalf("ParseIntentOutput with blank updated_at failed: %v", err)
}
if in.State != state.IntentNormal || in.Source != "peer" {
t.Fatalf("unexpected parsed intent payload: %+v", in)
}
withPrefix, err := state.ParseIntentOutput("status=ok intent=shutdown_complete reason=\"done\" source=daemon")
if err != nil {
t.Fatalf("ParseIntentOutput with prefixed tokens failed: %v", err)
}
if withPrefix.State != state.IntentShutdownComplete || withPrefix.Reason != "done" || withPrefix.Source != "daemon" {
t.Fatalf("unexpected prefixed parsed intent payload: %+v", withPrefix)
}
}
// TestStateIntentAutoHealFailureBranch runs one orchestration or CLI step.
// Signature: TestStateIntentAutoHealFailureBranch(t *testing.T).
// Why: covers ReadIntent branch where corrupt file quarantine fails and error details are returned.
func TestStateIntentAutoHealFailureBranch(t *testing.T) {
root := t.TempDir()
dir := filepath.Join(root, "ro")
if err := os.MkdirAll(dir, 0o700); err != nil {
t.Fatalf("mkdir readonly dir: %v", err)
}
path := filepath.Join(dir, "intent.json")
if err := os.WriteFile(path, []byte("{bad-json"), 0o600); err != nil {
t.Fatalf("write malformed intent file: %v", err)
}
if err := os.Chmod(dir, 0o500); err != nil {
t.Fatalf("chmod readonly dir: %v", err)
}
t.Cleanup(func() { _ = os.Chmod(dir, 0o700) })
_, err := state.ReadIntent(path)
if err == nil {
t.Fatalf("expected ReadIntent auto-heal failure for readonly dir")
}
if !strings.Contains(err.Error(), "auto-heal failed") {
t.Fatalf("expected auto-heal failure context, got %v", err)
}
}
// TestStateAcquireLockReclaimsNoPidLock runs one orchestration or CLI step.
// Signature: TestStateAcquireLockReclaimsNoPidLock(t *testing.T).
// Why: covers stale-lock parsing branch where lock file contains no pid line.
func TestStateAcquireLockReclaimsNoPidLock(t *testing.T) {
root := t.TempDir()
lockPath := filepath.Join(root, "ananke.lock")
if err := os.WriteFile(lockPath, []byte("started=2020-01-01T00:00:00Z\n"), 0o600); err != nil {
t.Fatalf("write no-pid lock: %v", err)
}
unlock, err := state.AcquireLock(lockPath)
if err != nil {
t.Fatalf("expected lock reclaim for no-pid lock, got %v", err)
}
unlock()
}