package config

import (
	"encoding/json"
	"os"
	"testing"
)

func TestArchInstallConfigGeneration(t *testing.T) {
	config := &InstallConfig{
		Disk:         "/dev/sda",
		EnableLUKS:   true,
		Hostname:     "miasma-test",
		Username:     "testuser",
		RootPassword: "rootpass",
		UserPassword: "userpass",
		Timezone:     "UTC",
		Locale:       "en_US.UTF-8",
	}

	archConfig := config.ToArchInstall()

	// Test that the config has the expected structure
	if archConfig.Version == "" {
		t.Error("Version should not be empty")
	}

	if archConfig.Bootloader != "Systemd-boot" {
		t.Errorf("Expected bootloader to be 'Systemd-boot', got '%s'", archConfig.Bootloader)
	}

	if len(archConfig.Kernels) != 1 || archConfig.Kernels[0] != "linux-hardened" {
		t.Errorf("Expected kernels to contain 'linux-hardened', got %v", archConfig.Kernels)
	}

	if archConfig.Hostname != "miasma-test" {
		t.Errorf("Expected hostname 'miasma-test', got '%s'", archConfig.Hostname)
	}

	// Test disk configuration
	if len(archConfig.DiskConfig.DeviceModifications) != 1 {
		t.Errorf("Expected 1 device modification, got %d", len(archConfig.DiskConfig.DeviceModifications))
	}

	deviceMod := archConfig.DiskConfig.DeviceModifications[0]
	if deviceMod.Device != "/dev/sda" {
		t.Errorf("Expected device '/dev/sda', got '%s'", deviceMod.Device)
	}

	if len(deviceMod.Partitions) != 2 {
		t.Errorf("Expected 2 partitions, got %d", len(deviceMod.Partitions))
	}

	// Test profile configuration
	if archConfig.ProfileConfig.Profile.Main != "Desktop" {
		t.Errorf("Expected profile main 'Desktop', got '%s'", archConfig.ProfileConfig.Profile.Main)
	}

	// Test user configuration
	if len(archConfig.AuthConfig.Users) != 1 {
		t.Errorf("Expected 1 user, got %d", len(archConfig.AuthConfig.Users))
	}

	user := archConfig.AuthConfig.Users[0]
	if user.Username != "testuser" {
		t.Errorf("Expected username 'testuser', got '%s'", user.Username)
	}

	// Test package list
	expectedPackages := []string{
		"base", "base-devel", "linux-hardened", "linux-firmware", "btrfs-progs",
		"neovim", "zsh", "alacritty", "tmux", "git", "opendoas",
		"firejail", "apparmor", "nftables", "hardened-malloc",
		"chromium", "xwayland-satellite",
		"cosmic-session", "cosmic-greeter", "cosmic-files",
		"cosmic-edit", "cosmic-term", "cosmic-store", "cosmic-settings",
	}

	for _, pkg := range expectedPackages {
		found := false
		for _, installedPkg := range archConfig.Packages {
			if installedPkg == pkg {
				found = true
				break
			}
		}
		if !found {
			t.Errorf("Expected package '%s' in package list", pkg)
		}
	}
}

func TestSaveConfigurationFiles(t *testing.T) {
	config := &InstallConfig{
		Disk:         "/dev/sda",
		EnableLUKS:   false,
		Hostname:     "miasma-test",
		Username:     "testuser",
		RootPassword: "rootpass",
		UserPassword: "userpass",
		Timezone:     "UTC",
		Locale:       "en_US.UTF-8",
	}

	// Test saving configuration
	err := config.SaveArchInstallConfig("/tmp/test_user_config.json")
	if err != nil {
		t.Fatalf("Failed to save user configuration: %v", err)
	}

	// Test saving credentials
	err = config.SaveUserCredentials("/tmp/test_user_creds.json")
	if err != nil {
		t.Fatalf("Failed to save user credentials: %v", err)
	}

	// Verify the files were created
	if _, err := os.Stat("/tmp/test_user_config.json"); os.IsNotExist(err) {
		t.Error("User configuration file was not created")
	}

	if _, err := os.Stat("/tmp/test_user_creds.json"); os.IsNotExist(err) {
		t.Error("User credentials file was not created")
	}

	// Verify the configuration file content
	data, err := os.ReadFile("/tmp/test_user_config.json")
	if err != nil {
		t.Fatalf("Failed to read configuration file: %v", err)
	}

	var parsedConfig ArchInstallConfig
	err = json.Unmarshal(data, &parsedConfig)
	if err != nil {
		t.Fatalf("Failed to parse configuration file: %v", err)
	}

	if parsedConfig.Hostname != "miasma-test" {
		t.Errorf("Expected hostname 'miasma-test', got '%s'", parsedConfig.Hostname)
	}

	// Clean up test files
	os.Remove("/tmp/test_user_config.json")
	os.Remove("/tmp/test_user_creds.json")
}