package installer

import (
	"fmt"
	"os"

	"gitea.unprism.ru/KRBL/FemaInstaller/internal/ssh"
	"gitea.unprism.ru/KRBL/FemaInstaller/pkg/config"
	"gitea.unprism.ru/KRBL/FemaInstaller/pkg/fileutils"
)

// Installer handles the installation process
type Installer struct {
	DefaultSettings string
}

// NewInstaller creates a new installer with the provided default settings
func NewInstaller(defaultSettings string) *Installer {
	return &Installer{
		DefaultSettings: defaultSettings,
	}
}

// Install performs the installation process
func (i *Installer) Install(sshConfig *config.SSHConfig) error {
	// Validate serial number
	if len([]rune(sshConfig.Serial)) != 16 {
		return fmt.Errorf("serial number must be 16 characters")
	}

	// Update settings with user configuration
	updatedSettings, err := config.UpdateSettingsJSON(i.DefaultSettings, sshConfig)
	if err != nil {
		return fmt.Errorf("failed to update settings: %w", err)
	}

	// Save updated settings to file
	err = config.SaveSettingsJSON(updatedSettings, "settings.json")
	if err != nil {
		return fmt.Errorf("failed to save settings: %w", err)
	}

	// Create SSH client configuration
	clientConfig := ssh.NewClientConfig(
		sshConfig.IP,
		sshConfig.Port,
		sshConfig.Login,
		sshConfig.Password,
	)

	// Connect to SSH server
	sshClient, err := ssh.CreateSSHClient(clientConfig)
	if err != nil {
		return fmt.Errorf("SSH connection failed: %w", err)
	}
	defer sshClient.Close()

	// Create SFTP client
	sftpClient, err := ssh.CreateSFTPClient(clientConfig)
	if err != nil {
		return fmt.Errorf("SFTP connection failed: %w", err)
	}
	defer sftpClient.Close()

	// Upload archive
	remotePath := "/root/dict.tar"
	if err = fileutils.UploadFile(sftpClient, sshConfig.ArchivePath, remotePath); err != nil {
		return fmt.Errorf("file upload failed: %w", err)
	}

	// Upload settings
	settingsPath := "/root/settings.json"
	if err = fileutils.UploadFile(sftpClient, "settings.json", settingsPath); err != nil {
		return fmt.Errorf("settings upload failed: %w", err)
	}

	// Execute installation commands
	commands := []string{
		"tar -xf /root/dict.tar -C /root/",
		"mkdir -p /root/fema/storage",
		"mv -f ~/settings.json /root/fema/storage",
		"chmod +x /root/dict/*",
		fmt.Sprintf("sudo /root/dict/install.sh -s %s", sshConfig.Serial),
	}

	for _, cmd := range commands {
		if err := ssh.ExecuteCommand(sshClient, cmd); err != nil {
			return fmt.Errorf("command execution failed: %w", err)
		}
	}

	// Clean up temporary files
	os.Remove("settings.json")

	return nil
}