package session

import (
	"fmt"

	"github.com/aki/amux/internal/cli/ui"
	"github.com/aki/amux/internal/session"
	"github.com/aki/amux/internal/worktree"
	"github.com/spf13/cobra"
)

var removeCmd = &cobra.Command{
	Use:   "remove <session-id>",
	Short: "Remove a stopped session",
	Long: `Remove a stopped session from the session list.

This command permanently removes session metadata. Only stopped sessions
can be removed. To stop a running session first, use 'amux session stop'.

If the session created its worktree automatically, the worktree will also
be removed unless --keep-worktree is specified.

Use --force to automatically stop a running session before removal.`,
	Args:    cobra.ExactArgs(1),
	Aliases: []string{"rm", "delete"},
	RunE:    RemoveSession,
}

var removeOpts struct {
	keepWorktree bool
	force        bool
}

func init() {
	removeCmd.Flags().BoolVar(&removeOpts.keepWorktree, "keep-worktree", false, "Keep auto-created worktree when removing session")
	removeCmd.Flags().BoolVarP(&removeOpts.force, "force", "f", false, "Force removal by stopping running sessions first")
}

// RemoveSession implements the session remove command
func RemoveSession(cmd *cobra.Command, args []string) error {
	ctx := cmd.Context()
	sessionID := args[0]

	// Setup managers with project root detection
	configMgr, sessionMgr, err := setupManagers()
	if err != nil {
		return err
	}

	// Get session to check its status and worktree
	sess, err := sessionMgr.Get(ctx, sessionID)
	if err != nil {
		return fmt.Errorf("session '%s' not found. Run 'amux ps' to see active sessions", sessionID)
	}

	// Check if session is running
	if sess.Status == session.StatusRunning {
		if !removeOpts.force {
			return fmt.Errorf("cannot remove running session %s (use 'amux session stop' first or --force)", sessionID)
		}
		// Force flag is set, stop the session first
		ui.Info("Stopping running session %s...", sessionID)
		if err := sessionMgr.Stop(ctx, sessionID); err != nil {
			return fmt.Errorf("failed to stop session: %w", err)
		}
		ui.Success("Session stopped successfully")
	}

	// Save worktree branch before removing session
	worktreeBranch := sess.WorktreeBranch

	// Remove the session
	if err := sessionMgr.Remove(ctx, sessionID); err != nil {
		return fmt.Errorf("failed to remove session '%s': %w", sessionID, err)
	}

	ui.Success("Session removed: %s", sessionID)

	// Check if worktree was auto-created and --keep-worktree was not specified
	if !removeOpts.keepWorktree && worktreeBranch != "" {
		// Create worktree manager
		wtMgr, err := worktree.SetupManager(configMgr.GetProjectRoot())
		if err != nil {
			// If we can't create worktree manager, skip worktree removal silently
			return nil //nolint:nilerr // Intentionally returning nil to continue gracefully
		}

		// Get worktree to check if it was auto-created
		wt, err := wtMgr.Get(ctx, worktreeBranch)
		if err != nil {
			// Worktree might already be removed or not found, skip auto-removal silently
			return nil //nolint:nilerr // Intentionally returning nil to continue gracefully
		}

		// If worktree was auto-created, try to remove it
		if wt.AutoCreated {
			// Check if any other sessions are using this worktree
			sessions, err := sessionMgr.List(ctx, "")
			if err != nil {
				ui.Warning("Failed to check for other sessions using worktree: %v", err)
				return nil
			}

			// Check if any other session is using the same worktree
			worktreeInUse := false
			for _, otherSession := range sessions {
				if otherSession.WorktreeBranch == worktreeBranch {
					worktreeInUse = true
					break
				}
			}

			if !worktreeInUse {
				// Remove the worktree
				if err := wtMgr.Remove(ctx, worktree.Identifier(worktreeBranch), worktree.RemoveOptions{NoHooks: false}); err != nil {
					ui.Warning("Failed to remove auto-created worktree %s: %v", wt.Branch, err)
				} else {
					ui.OutputLine("Removed auto-created worktree: '%s'", wt.Branch)
				}
			} else {
				ui.Info("Auto-created worktree not removed (still in use by other sessions)")
			}
		}
	}

	return nil
}
