package cmd

import (
	"encoding/json"
	"fmt"
	"os"
	"text/tabwriter"

	"github.com/spf13/cobra"

	"github.com/nextlevelbuilder/goclaw/internal/config"
)

func modelsCmd() *cobra.Command {
	cmd := &cobra.Command{
		Use:   "models",
		Short: "List available AI models and providers",
	}
	cmd.AddCommand(modelsListCmd())
	return cmd
}

type modelEntry struct {
	Provider string `json:"provider"`
	Model    string `json:"model"`
	Status   string `json:"status"`
}

func modelsListCmd() *cobra.Command {
	var jsonOutput bool
	cmd := &cobra.Command{
		Use:   "list",
		Short: "List configured models and providers",
		Run: func(cmd *cobra.Command, args []string) {
			cfgPath := resolveConfigPath()
			cfg, err := config.Load(cfgPath)
			if err != nil {
				fmt.Fprintf(os.Stderr, "Error loading config: %s\n", err)
				os.Exit(1)
			}

			entries := buildModelList(cfg)

			if jsonOutput {
				data, _ := json.MarshalIndent(entries, "", "  ")
				fmt.Println(string(data))
				return
			}

			tw := tabwriter.NewWriter(os.Stdout, 0, 0, 2, ' ', 0)
			fmt.Fprintf(tw, "PROVIDER\tMODEL\tSTATUS\n")
			for _, e := range entries {
				fmt.Fprintf(tw, "%s\t%s\t%s\n", e.Provider, e.Model, e.Status)
			}
			tw.Flush()
		},
	}
	cmd.Flags().BoolVar(&jsonOutput, "json", false, "output as JSON")
	return cmd
}

func buildModelList(cfg *config.Config) []modelEntry {
	var entries []modelEntry

	// Default agent model
	entries = append(entries, modelEntry{
		Provider: cfg.Agents.Defaults.Provider,
		Model:    cfg.Agents.Defaults.Model,
		Status:   "default",
	})

	// Per-agent overrides
	for id, spec := range cfg.Agents.List {
		if spec.Model != "" {
			entries = append(entries, modelEntry{
				Provider: spec.Provider,
				Model:    spec.Model,
				Status:   "agent:" + id,
			})
		}
	}

	// Available providers
	type providerCheck struct {
		name   string
		hasKey bool
	}
	providers := []providerCheck{
		{"anthropic", cfg.Providers.Anthropic.APIKey != ""},
		{"openai", cfg.Providers.OpenAI.APIKey != ""},
		{"openrouter", cfg.Providers.OpenRouter.APIKey != ""},
		{"gemini", cfg.Providers.Gemini.APIKey != ""},
		{"groq", cfg.Providers.Groq.APIKey != ""},
		{"deepseek", cfg.Providers.DeepSeek.APIKey != ""},
		{"mistral", cfg.Providers.Mistral.APIKey != ""},
		{"xai", cfg.Providers.XAI.APIKey != ""},
	}
	for _, p := range providers {
		if p.hasKey {
			entries = append(entries, modelEntry{
				Provider: p.name,
				Model:    "(any)",
				Status:   "available",
			})
		}
	}

	return entries
}
