package handlers

import (
	"net/http"

	"github.com/gin-gonic/gin"

	"switchboard-core/models"
	"switchboard-core/store"
)

// ExtSecretsHandler serves extension secret management endpoints.
// v0.29.0 CS3: Admin sets key-value secrets that Starlark extensions
// can read via the secrets.get() module.
//
// Secrets are stored in GlobalConfig under key "ext_secrets:{packageID}"
// as a JSON map: {"api_key": "sk-...", "webhook_token": "tok-..."}.
type ExtSecretsHandler struct {
	stores store.Stores
}

func NewExtSecretsHandler(stores store.Stores) *ExtSecretsHandler {
	return &ExtSecretsHandler{stores: stores}
}

// GetSecrets returns the secret keys (not values) for a package.
// GET /api/v1/admin/extensions/:id/secrets
func (h *ExtSecretsHandler) GetSecrets(c *gin.Context) {
	pkgID := c.Param("id")
	configKey := "ext_secrets:" + pkgID

	configVal, err := h.stores.GlobalConfig.Get(c.Request.Context(), configKey)
	if err != nil {
		// Not found = empty secrets, not an error
		c.JSON(http.StatusOK, gin.H{"data": map[string]string{}})
		return
	}

	// Return only keys, not values (security: don't expose secrets in GET)
	keys := make([]string, 0, len(configVal))
	for k := range configVal {
		keys = append(keys, k)
	}

	c.JSON(http.StatusOK, gin.H{"data": gin.H{
		"package_id": pkgID,
		"keys":       keys,
	}})
}

// SetSecrets upserts secrets for a package.
// PUT /api/v1/admin/extensions/:id/secrets
// Body: {"secrets": {"api_key": "sk-...", "webhook_token": "tok-..."}}
func (h *ExtSecretsHandler) SetSecrets(c *gin.Context) {
	pkgID := c.Param("id")
	userID := c.GetString("user_id")

	// Verify package exists
	pkg, err := h.stores.Packages.Get(c.Request.Context(), pkgID)
	if err != nil || pkg == nil {
		c.JSON(http.StatusNotFound, gin.H{"error": "package not found"})
		return
	}

	var body struct {
		Secrets map[string]string `json:"secrets" binding:"required"`
	}
	if err := c.ShouldBindJSON(&body); err != nil {
		c.JSON(http.StatusBadRequest, gin.H{"error": "invalid request: " + err.Error()})
		return
	}

	// Store as GlobalConfig JSONMap
	configKey := "ext_secrets:" + pkgID
	configVal := models.JSONMap{}
	for k, v := range body.Secrets {
		configVal[k] = v
	}

	if err := h.stores.GlobalConfig.Set(c.Request.Context(), configKey, configVal, userID); err != nil {
		c.JSON(http.StatusInternalServerError, gin.H{"error": "failed to save secrets"})
		return
	}

	c.JSON(http.StatusOK, gin.H{
		"status":     "saved",
		"package_id": pkgID,
		"key_count":  len(body.Secrets),
	})
}

// DeleteSecrets removes all secrets for a package.
// DELETE /api/v1/admin/extensions/:id/secrets
func (h *ExtSecretsHandler) DeleteSecrets(c *gin.Context) {
	pkgID := c.Param("id")
	userID := c.GetString("user_id")

	configKey := "ext_secrets:" + pkgID
	if err := h.stores.GlobalConfig.Set(c.Request.Context(), configKey, models.JSONMap{}, userID); err != nil {
		c.JSON(http.StatusInternalServerError, gin.H{"error": "failed to delete secrets"})
		return
	}

	c.JSON(http.StatusOK, gin.H{"status": "deleted", "package_id": pkgID})
}
