package webui

import (
	"net/http"
	"net/http/httptest"
	"net/url"
	"strings"
	"testing"
)

// TestLetsEncryptSaveBlankMeansKeepExisting confirms a secret field submitted blank
// doesn't wipe a previously-saved credential, while a non-empty submission does
// overwrite it — the whole reason this page has its own save handler instead of using
// the generic settingsUpdate reflection.
func TestLetsEncryptSaveBlankMeansKeepExisting(t *testing.T) {
	app := newTestApp(t)
	mux := app.Mux()
	cookie := loginSession(t, app)

	app.Cfg.Section("LetsEncrypt").Key("cloudflare_api_token").SetValue("original-secret-token")

	// Submit the form with the secret field blank (and a plain field changed).
	form := url.Values{
		"enabled":       {"true"},
		"dns_provider":  {"cloudflare"},
		"domains":       {"mail.example.com"},
		"contact_email": {"admin@example.com"},
	}
	req := httptest.NewRequest(http.MethodPost, Prefix+"/letsencrypt/save", strings.NewReader(form.Encode()))
	req.Header.Set("Content-Type", "application/x-www-form-urlencoded")
	req.AddCookie(cookie)
	rec := httptest.NewRecorder()
	mux.ServeHTTP(rec, req)
	if rec.Code != http.StatusFound {
		t.Fatalf("expected redirect, got %d: %s", rec.Code, rec.Body.String())
	}
	if got := app.Cfg.Section("LetsEncrypt").Key("cloudflare_api_token").String(); got != "original-secret-token" {
		t.Fatalf("expected the blank submission to keep the existing token, got %q", got)
	}
	if got := app.Cfg.Section("LetsEncrypt").Key("enabled").String(); got != "true" {
		t.Fatalf("expected the plain field to be updated, got %q", got)
	}

	// Now submit a real value for the secret field — it must overwrite.
	form.Set("cloudflare_api_token", "new-secret-token")
	req2 := httptest.NewRequest(http.MethodPost, Prefix+"/letsencrypt/save", strings.NewReader(form.Encode()))
	req2.Header.Set("Content-Type", "application/x-www-form-urlencoded")
	req2.AddCookie(cookie)
	rec2 := httptest.NewRecorder()
	mux.ServeHTTP(rec2, req2)
	if rec2.Code != http.StatusFound {
		t.Fatalf("expected redirect, got %d", rec2.Code)
	}
	if got := app.Cfg.Section("LetsEncrypt").Key("cloudflare_api_token").String(); got != "new-secret-token" {
		t.Fatalf("expected a non-empty submission to overwrite the token, got %q", got)
	}
}

// TestLetsEncryptPageNeverRendersSecrets confirms secret fields are always blank in
// the rendered form, even when a value is stored.
func TestLetsEncryptPageNeverRendersSecrets(t *testing.T) {
	app := newTestApp(t)
	mux := app.Mux()
	cookie := loginSession(t, app)
	app.Cfg.Section("LetsEncrypt").Key("cloudflare_api_token").SetValue("super-secret-value")

	req := httptest.NewRequest(http.MethodGet, Prefix+"/letsencrypt", nil)
	req.AddCookie(cookie)
	rec := httptest.NewRecorder()
	mux.ServeHTTP(rec, req)
	if rec.Code != http.StatusOK {
		t.Fatalf("status = %d", rec.Code)
	}
	if strings.Contains(rec.Body.String(), "super-secret-value") {
		t.Fatal("expected the stored secret to never be rendered back into the page")
	}
}
