package api

import (
	"net/http"
	"testing"
)

// TestSavePreferences_EmptyEmailCannotClobber (v0.71.0 F12, Scenario E): a controller push with an
// empty email must preserve a stored non-empty address while still applying events + cooldown.
// Companion red-proof: removing the guard in handleSavePreferences makes this fail.
func TestSavePreferences_EmptyEmailCannotClobber(t *testing.T) {
	h, st := newEventTestHandler(t)
	if err := st.SaveNotificationPrefs("c1", "seeded@example.hu", []string{"node_down", "backup_failed"}, 6); err != nil {
		t.Fatalf("stored prefs: %v", err)
	}

	rr := do(h, http.MethodPost, "/preferences", "ckey",
		`{"customer_id":"c1","email":"","enabled_events":["node_down"],"cooldown_hours":12}`)
	if rr.Code != http.StatusOK {
		t.Fatalf("status = %d, body=%s", rr.Code, rr.Body.String())
	}

	prefs, err := st.GetNotificationPrefs("c1")
	if err != nil || prefs == nil {
		t.Fatalf("prefs: %+v err=%v", prefs, err)
	}
	if prefs.Email != "seeded@example.hu" {
		t.Fatalf("empty-email push CLOBBERED the stored address: email=%q", prefs.Email)
	}
	if len(prefs.EnabledEvents) != 1 || prefs.EnabledEvents[0] != "node_down" || prefs.CooldownHours != 12 {
		t.Fatalf("events/cooldown from the push must still apply: %+v", prefs)
	}
}

// TestSavePreferences_NonEmptyEmailStillUpdates: a push with a real email updates everything —
// customer edits keep working (the guard must not freeze the address forever).
func TestSavePreferences_NonEmptyEmailStillUpdates(t *testing.T) {
	h, st := newEventTestHandler(t)
	if err := st.SaveNotificationPrefs("c1", "old@example.hu", []string{"node_down"}, 6); err != nil {
		t.Fatalf("stored prefs: %v", err)
	}

	rr := do(h, http.MethodPost, "/preferences", "ckey",
		`{"customer_id":"c1","email":"new@example.hu","enabled_events":["backup_failed"],"cooldown_hours":3}`)
	if rr.Code != http.StatusOK {
		t.Fatalf("status = %d, body=%s", rr.Code, rr.Body.String())
	}
	prefs, _ := st.GetNotificationPrefs("c1")
	if prefs.Email != "new@example.hu" || len(prefs.EnabledEvents) != 1 || prefs.EnabledEvents[0] != "backup_failed" || prefs.CooldownHours != 3 {
		t.Fatalf("non-empty push must update everything: %+v", prefs)
	}
}

// TestSavePreferences_EmptyEmailNoStoredRow: an empty-email push with no stored row behaves as
// before (row created with empty email — the all-off case stays legitimate).
func TestSavePreferences_EmptyEmailNoStoredRow(t *testing.T) {
	h, st := newEventTestHandler(t)
	rr := do(h, http.MethodPost, "/preferences", "ckey",
		`{"customer_id":"c1","email":"","enabled_events":[],"cooldown_hours":6}`)
	if rr.Code != http.StatusOK {
		t.Fatalf("status = %d, body=%s", rr.Code, rr.Body.String())
	}
	prefs, _ := st.GetNotificationPrefs("c1")
	if prefs == nil || prefs.Email != "" {
		t.Fatalf("all-off push must store the empty row unchanged, got %+v", prefs)
	}
}
