package admin

import (
	"github.com/gofiber/fiber/v2"
	"go.uber.org/zap"

	"github.com/break/junhong_cmp_fiber/internal/model/dto"
	"github.com/break/junhong_cmp_fiber/pkg/errors"
	"github.com/break/junhong_cmp_fiber/pkg/logger"
	"github.com/break/junhong_cmp_fiber/pkg/response"
	"github.com/break/junhong_cmp_fiber/pkg/storage"
)

type StorageHandler struct {
	service *storage.Service
}

func NewStorageHandler(service *storage.Service) *StorageHandler {
	return &StorageHandler{service: service}
}

// GetBatchDownloadURLs 批量获取文件下载预签名 URL
// POST /api/admin/storage/batch-download-urls
func (h *StorageHandler) GetBatchDownloadURLs(c *fiber.Ctx) error {
	if h.service == nil {
		return errors.New(errors.CodeInternalError, "对象存储服务未配置")
	}

	var req dto.GetBatchDownloadURLsRequest
	if err := c.BodyParser(&req); err != nil {
		return errors.New(errors.CodeInvalidParam)
	}

	urls := make(map[string]string, len(req.FileKeys))
	expiresIn := 0

	for _, fileKey := range req.FileKeys {
		result, err := h.service.GetDownloadURL(c.UserContext(), fileKey)
		if err != nil {
			logger.GetAppLogger().Error("获取下载URL失败",
				zap.String("file_key", fileKey),
				zap.Error(err),
			)
			return errors.New(errors.CodeInternalError, "获取下载URL失败")
		}
		urls[fileKey] = result.URL
		expiresIn = result.ExpiresIn
	}

	return response.Success(c, dto.GetBatchDownloadURLsResponse{
		URLs:      urls,
		ExpiresIn: expiresIn,
	})
}

// GetUploadURL 获取文件上传预签名 URL
// POST /api/admin/storage/upload-url
func (h *StorageHandler) GetUploadURL(c *fiber.Ctx) error {
	if h.service == nil {
		return errors.New(errors.CodeInternalError, "对象存储服务未配置")
	}

	var req dto.GetUploadURLRequest
	if err := c.BodyParser(&req); err != nil {
		return errors.New(errors.CodeInvalidParam, "请求参数解析失败")
	}

	result, err := h.service.GetUploadURL(c.UserContext(), req.Purpose, req.FileName, req.ContentType)
	if err != nil {
		logger.GetAppLogger().Error("获取上传URL失败",
			zap.String("path", c.Path()),
			zap.String("method", c.Method()),
			zap.String("purpose", req.Purpose),
			zap.String("fileName", req.FileName),
			zap.Error(err),
		)
		return errors.New(errors.CodeInternalError, "获取上传URL失败")
	}

	return response.Success(c, dto.GetUploadURLResponse{
		UploadURL: result.URL,
		FileKey:   result.FileKey,
		ExpiresIn: result.ExpiresIn,
	})
}
