package miragebrand

import (
	"path/filepath"
	"slices"
	"testing"
)

func TestWindowsPipePath(t *testing.T) {
	got := WindowsPipePath()
	want := `\\.\pipe\ProtectedPrefix\Administrators\Mirage\miraged`
	if got != want {
		t.Fatalf("WindowsPipePath() = %q, want %q", got, want)
	}
}

func TestWindowsStateFile(t *testing.T) {
	got := WindowsStateFile(`C:\ProgramData`)
	want := filepath.Join(`C:\ProgramData`, "Mirage", "server-state.conf")
	if got != want {
		t.Fatalf("WindowsStateFile() = %q, want %q", got, want)
	}
}

func TestWindowsLegacyStateFile(t *testing.T) {
	got := WindowsLegacyStateFile(`C:\Users\alice\AppData\Local`)
	want := filepath.Join(`C:\Users\alice\AppData\Local`, "Mirage", "server-state.conf")
	if got != want {
		t.Fatalf("WindowsLegacyStateFile() = %q, want %q", got, want)
	}
}

func TestRegistryPaths(t *testing.T) {
	if got, want := RegistryBase(), `SOFTWARE\Mirage IPN`; got != want {
		t.Fatalf("RegistryBase() = %q, want %q", got, want)
	}
	if got, want := PolicyRegistryBase(), `SOFTWARE\Policies\Mirage`; got != want {
		t.Fatalf("PolicyRegistryBase() = %q, want %q", got, want)
	}
}

func TestWindowsKnownProcessNames(t *testing.T) {
	got := WindowsKnownProcessNames()
	for _, want := range []string{"mirage", "miraged"} {
		if !slices.Contains(got, want) {
			t.Fatalf("WindowsKnownProcessNames() = %v, missing %q", got, want)
		}
	}
}

func TestWindowsExecutableNames(t *testing.T) {
	if got, want := WindowsGUIExecutableName(), "MirageGUI.exe"; got != want {
		t.Fatalf("WindowsGUIExecutableName() = %q, want %q", got, want)
	}
	if got, want := WindowsCLIExecutableName(), "mirage.exe"; got != want {
		t.Fatalf("WindowsCLIExecutableName() = %q, want %q", got, want)
	}
	if got := WindowsLegacyGUIExecutableNames(); !slices.Equal(got, []string{"MirageGUI.exe", "Mirage.exe"}) {
		t.Fatalf("WindowsLegacyGUIExecutableNames() = %v, want [MirageGUI.exe Mirage.exe]", got)
	}
}

func TestIsMirageBinaryName(t *testing.T) {
	tests := map[string]bool{
		"mirage":       true,
		"mirage-cli":   true,
		"miraged":      true,
		"mirage-qt":    true,
		"mirage-qt-ui": true,
		"tailscale":    false,
		"tailscaled":   false,
		"cli.test":     false,
	}
	for input, want := range tests {
		if got := IsMirageBinaryName(input); got != want {
			t.Fatalf("IsMirageBinaryName(%q) = %v, want %v", input, got, want)
		}
	}
}

func TestLinuxBrandingDefaults(t *testing.T) {
	if got, want := LinuxSocketPath(), "/run/mirage/miraged.sock"; got != want {
		t.Fatalf("LinuxSocketPath() = %q, want %q", got, want)
	}
	if got, want := LinuxStateFile(), "/var/lib/mirage/miraged.state"; got != want {
		t.Fatalf("LinuxStateFile() = %q, want %q", got, want)
	}
	if got, want := LinuxServiceUnit(), "miraged.service"; got != want {
		t.Fatalf("LinuxServiceUnit() = %q, want %q", got, want)
	}
	if got, want := LinuxTunName(), "mirage0"; got != want {
		t.Fatalf("LinuxTunName() = %q, want %q", got, want)
	}
	if got, want := CanonicalCLIName("mirage-cli"), "mirage"; got != want {
		t.Fatalf("CanonicalCLIName(mirage-cli) = %q, want %q", got, want)
	}
	if got, want := CanonicalCLIName("tailscale"), "tailscale"; got != want {
		t.Fatalf("CanonicalCLIName(tailscale) = %q, want %q", got, want)
	}
}

func TestDaemonBrandingNames(t *testing.T) {
	if got, want := WindowsTunName(), "Mirage"; got != want {
		t.Fatalf("WindowsTunName() = %q, want %q", got, want)
	}
	if got, want := LinuxStateFileBaseName(), "miraged.state"; got != want {
		t.Fatalf("LinuxStateFileBaseName() = %q, want %q", got, want)
	}
	if got, want := DaemonBinaryName(), "miraged"; got != want {
		t.Fatalf("DaemonBinaryName() = %q, want %q", got, want)
	}
}
