Files
shangbangbang/internal/handlers/admin_product_handler.go
solosw 99b11b04e4 1.0
2026-01-05 14:11:34 +08:00

512 lines
15 KiB
Go

package handlers
import (
"awesomeProject/internal/common"
"awesomeProject/internal/models"
"fmt"
"net/http"
"strconv"
"github.com/gin-gonic/gin"
"gorm.io/gorm"
)
// AdminProductHandler 管理端商品处理器
type AdminProductHandler struct{}
// CreateProductCategoryRequest 创建商品分类请求结构体
type CreateProductCategoryRequest struct {
CategoryName string `json:"category_name" binding:"required"`
CategoryIcon string `json:"category_icon"`
SortOrder int `json:"sort_order"`
Status uint8 `json:"status"`
}
// UpdateProductCategoryRequest 更新商品分类请求结构体
type UpdateProductCategoryRequest struct {
CategoryName string `json:"category_name"`
CategoryIcon string `json:"category_icon"`
SortOrder int `json:"sort_order"`
Status uint8 `json:"status"`
}
// GetProductCategories 获取商品分类列表
func (h *AdminProductHandler) GetProductCategories(c *gin.Context) {
var categories []models.ProductCategory
err := common.GetDB().Order("sort_order ASC, created_at DESC").Find(&categories).Error
if err != nil {
c.JSON(http.StatusOK, common.Error(500, "查询商品分类失败"))
return
}
c.JSON(http.StatusOK, common.Success(categories))
}
// CreateProductCategory 创建商品分类(仅管理员)
func (h *AdminProductHandler) CreateProductCategory(c *gin.Context) {
currentUser, _ := c.Get("current_user")
user := currentUser.(models.User)
// 只有管理员可以创建分类
if user.SystemRole != 0 {
c.JSON(http.StatusOK, common.Error(403, "权限不足"))
return
}
var req CreateProductCategoryRequest
if err := c.ShouldBindJSON(&req); err != nil {
c.JSON(http.StatusOK, common.Error(400, "参数错误: "+err.Error()))
return
}
// 创建分类对象
newCategory := models.ProductCategory{
CategoryName: req.CategoryName,
CategoryIcon: req.CategoryIcon,
SortOrder: req.SortOrder,
Status: req.Status,
}
// 保存分类
if err := common.GetDB().Create(&newCategory).Error; err != nil {
c.JSON(http.StatusOK, common.Error(500, "创建商品分类失败"))
return
}
c.JSON(http.StatusOK, common.Success(newCategory))
}
// UpdateProductCategory 更新商品分类(仅管理员)
func (h *AdminProductHandler) UpdateProductCategory(c *gin.Context) {
currentUser, _ := c.Get("current_user")
user := currentUser.(models.User)
// 只有管理员可以更新分类
if user.SystemRole != 0 {
c.JSON(http.StatusOK, common.Error(403, "权限不足"))
return
}
categoryID, err := strconv.ParseUint(c.Param("id"), 10, 32)
if err != nil {
c.JSON(http.StatusOK, common.Error(400, "分类ID无效"))
return
}
var req UpdateProductCategoryRequest
if err := c.ShouldBindJSON(&req); err != nil {
c.JSON(http.StatusOK, common.Error(400, "参数错误: "+err.Error()))
return
}
// 检查分类是否存在
var existCategory models.ProductCategory
if err := common.GetDB().First(&existCategory, uint(categoryID)).Error; err != nil {
c.JSON(http.StatusOK, common.Error(404, "商品分类不存在"))
return
}
// 准备更新数据
updateData := models.ProductCategory{
CategoryName: req.CategoryName,
CategoryIcon: req.CategoryIcon,
SortOrder: req.SortOrder,
Status: req.Status,
}
// 更新分类信息
updateData.ID = uint(categoryID)
if err := common.GetDB().Model(&existCategory).Updates(&updateData).Error; err != nil {
c.JSON(http.StatusOK, common.Error(500, "更新商品分类失败"))
return
}
// 返回更新后的分类信息
var updatedCategory models.ProductCategory
common.GetDB().First(&updatedCategory, uint(categoryID))
c.JSON(http.StatusOK, common.Success(updatedCategory))
}
// DeleteProductCategory 删除商品分类(仅管理员)
func (h *AdminProductHandler) DeleteProductCategory(c *gin.Context) {
currentUser, _ := c.Get("current_user")
user := currentUser.(models.User)
// 只有管理员可以删除分类
if user.SystemRole != 0 {
c.JSON(http.StatusOK, common.Error(403, "权限不足"))
return
}
categoryID, err := strconv.ParseUint(c.Param("id"), 10, 32)
if err != nil {
c.JSON(http.StatusOK, common.Error(400, "分类ID无效"))
return
}
// 检查分类下是否有商品
var productCount int64
common.GetDB().Model(&models.PrimaryProduct{}).Where("category_id = ?", categoryID).Count(&productCount)
if productCount > 0 {
c.JSON(http.StatusOK, common.Error(400, "该分类下还有商品,无法删除"))
return
}
// 删除分类
if err := common.GetDB().Delete(&models.ProductCategory{}, uint(categoryID)).Error; err != nil {
c.JSON(http.StatusOK, common.Error(500, "删除商品分类失败"))
return
}
c.JSON(http.StatusOK, common.Success(nil))
}
// GetPrimaryProducts 获取一级商品列表
func (h *AdminProductHandler) GetPrimaryProducts(c *gin.Context) {
// 分页参数
page, _ := strconv.Atoi(c.DefaultQuery("page", "1"))
pageSize, _ := strconv.Atoi(c.DefaultQuery("page_size", "10"))
if page < 1 {
page = 1
}
if pageSize < 1 || pageSize > 100 {
pageSize = 10
}
// 搜索参数
categoryID := c.Query("category_id")
productName := c.Query("product_name")
status := c.Query("status")
db := common.GetDB()
var products []models.PrimaryProduct
var total int64
// 构建查询条件
query := db.Model(&models.PrimaryProduct{}).Preload("Category")
// 添加搜索条件
if categoryID != "" {
query = query.Where("category_id = ?", categoryID)
}
if productName != "" {
query = query.Where("product_name LIKE ?", "%"+productName+"%")
}
if status != "" {
query = query.Where("status = ?", status)
}
// 获取总数
query.Count(&total)
// 分页查询
offset := (page - 1) * pageSize
err := query.Offset(offset).Limit(pageSize).Order("sort_order ASC, created_at DESC").Find(&products).Error
if err != nil {
c.JSON(http.StatusOK, common.Error(500, "查询商品列表失败"))
return
}
// 构建返回数据
result := map[string]interface{}{
"list": products,
"total": total,
"page": page,
"page_size": pageSize,
}
c.JSON(http.StatusOK, common.Success(result))
}
// GetPrimaryProduct 获取单个一级商品详情
func (h *AdminProductHandler) GetPrimaryProduct(c *gin.Context) {
productID, err := strconv.ParseUint(c.Param("id"), 10, 32)
if err != nil {
c.JSON(http.StatusOK, common.Error(400, "商品ID无效"))
return
}
var product models.PrimaryProduct
err = common.GetDB().Preload("Category").First(&product, uint(productID)).Error
if err != nil {
if err == gorm.ErrRecordNotFound {
c.JSON(http.StatusOK, common.Error(404, "商品不存在"))
} else {
c.JSON(http.StatusOK, common.Error(500, "查询商品详情失败"))
}
return
}
c.JSON(http.StatusOK, common.Success(product))
}
// CreatePrimaryProductRequest 创建一级商品请求结构体
type CreatePrimaryProductRequest struct {
CategoryID uint `json:"category_id" binding:"required"`
ProductName string `json:"product_name" binding:"required"`
ProductDescription string `json:"product_description"`
ProductImages string `json:"product_images"`
OriginalPrice float64 `json:"original_price" binding:"required"`
CurrentPrice float64 `json:"current_price" binding:"required"`
StockQuantity int `json:"stock_quantity"`
SortOrder int `json:"sort_order"`
Status uint8 `json:"status"`
IsHot int8 `json:"is_hot"`
}
// CreatePrimaryProduct 创建一级商品(仅管理员)
func (h *AdminProductHandler) CreatePrimaryProduct(c *gin.Context) {
currentUser, _ := c.Get("current_user")
user := currentUser.(models.User)
// 只有管理员可以创建商品
if user.SystemRole != 0 {
c.JSON(http.StatusOK, common.Error(403, "权限不足"))
return
}
var req CreatePrimaryProductRequest
if err := c.ShouldBindJSON(&req); err != nil {
c.JSON(http.StatusOK, common.Error(400, "参数错误: "+err.Error()))
return
}
// 检查分类是否存在
var category models.ProductCategory
if err := common.GetDB().First(&category, req.CategoryID).Error; err != nil {
c.JSON(http.StatusOK, common.Error(404, "商品分类不存在"))
return
}
// 创建商品对象
newProduct := models.PrimaryProduct{
CategoryID: req.CategoryID,
ProductName: req.ProductName,
ProductDescription: req.ProductDescription,
ProductImages: req.ProductImages,
OriginalPrice: req.OriginalPrice,
CurrentPrice: req.CurrentPrice,
StockQuantity: req.StockQuantity,
SortOrder: req.SortOrder,
Status: req.Status,
IsHot: req.IsHot,
}
// 保存商品
if err := common.GetDB().Create(&newProduct).Error; err != nil {
c.JSON(http.StatusOK, common.Error(500, "创建商品失败"))
return
}
// 返回创建的商品(包含分类信息)
var createdProduct models.PrimaryProduct
common.GetDB().Preload("Category").First(&createdProduct, newProduct.ID)
c.JSON(http.StatusOK, common.Success(createdProduct))
}
// UpdatePrimaryProductRequest 更新一级商品请求结构体
type UpdatePrimaryProductRequest struct {
CategoryID uint `json:"category_id"`
ProductName string `json:"product_name"`
ProductDescription string `json:"product_description"`
ProductImages string `json:"product_images"`
OriginalPrice float64 `json:"original_price"`
CurrentPrice float64 `json:"current_price"`
StockQuantity int `json:"stock_quantity"`
SortOrder int `json:"sort_order"`
Status uint8 `json:"status"`
IsHot int8 `json:"is_hot"`
}
// UpdatePrimaryProduct 更新一级商品(仅管理员)
func (h *AdminProductHandler) UpdatePrimaryProduct(c *gin.Context) {
currentUser, _ := c.Get("current_user")
user := currentUser.(models.User)
// 只有管理员可以更新商品
if user.SystemRole != 0 {
c.JSON(http.StatusOK, common.Error(403, "权限不足"))
return
}
productID, err := strconv.ParseUint(c.Param("id"), 10, 32)
if err != nil {
c.JSON(http.StatusOK, common.Error(400, "商品ID无效"))
return
}
var req UpdatePrimaryProductRequest
if err := c.ShouldBindJSON(&req); err != nil {
c.JSON(http.StatusOK, common.Error(400, "参数错误: "+err.Error()))
return
}
// 检查商品是否存在
var existProduct models.PrimaryProduct
if err := common.GetDB().First(&existProduct, uint(productID)).Error; err != nil {
c.JSON(http.StatusOK, common.Error(404, "商品不存在"))
return
}
// 如果更新了分类,检查分类是否存在
if req.CategoryID != 0 {
var category models.ProductCategory
if err := common.GetDB().First(&category, req.CategoryID).Error; err != nil {
c.JSON(http.StatusOK, common.Error(404, "商品分类不存在"))
return
}
}
// 准备更新数据
updateData := models.PrimaryProduct{
CategoryID: req.CategoryID,
ProductName: req.ProductName,
ProductDescription: req.ProductDescription,
ProductImages: req.ProductImages,
OriginalPrice: req.OriginalPrice,
CurrentPrice: req.CurrentPrice,
StockQuantity: req.StockQuantity,
SortOrder: req.SortOrder,
Status: req.Status,
IsHot: req.IsHot,
}
fmt.Println(updateData.IsHot)
// 更新商品信息
updateData.ID = uint(productID)
if err := common.GetDB().Model(&existProduct).Updates(&updateData).Error; err != nil {
c.JSON(http.StatusOK, common.Error(500, "更新商品失败"))
return
}
common.GetDB().Model(&existProduct).Select("status", "is_hot").
Updates(models.PrimaryProduct{IsHot: req.IsHot, Status: req.Status})
// 返回更新后的商品信息
var updatedProduct models.PrimaryProduct
common.GetDB().Preload("Category").First(&updatedProduct, uint(productID))
c.JSON(http.StatusOK, common.Success(updatedProduct))
}
// DeletePrimaryProduct 删除一级商品(仅管理员)
func (h *AdminProductHandler) DeletePrimaryProduct(c *gin.Context) {
currentUser, _ := c.Get("current_user")
user := currentUser.(models.User)
// 只有管理员可以删除商品
if user.SystemRole != 0 {
c.JSON(http.StatusOK, common.Error(403, "权限不足"))
return
}
productID, err := strconv.ParseUint(c.Param("id"), 10, 32)
if err != nil {
c.JSON(http.StatusOK, common.Error(400, "商品ID无效"))
return
}
// 检查商品是否存在
var existProduct models.PrimaryProduct
if err := common.GetDB().First(&existProduct, uint(productID)).Error; err != nil {
c.JSON(http.StatusOK, common.Error(404, "商品不存在"))
return
}
// 删除商品
if err := common.GetDB().Delete(&existProduct).Error; err != nil {
c.JSON(http.StatusOK, common.Error(500, "删除商品失败"))
return
}
c.JSON(http.StatusOK, common.Success(nil))
}
// GetSecondaryProducts 获取二级商品列表
func (h *AdminProductHandler) GetSecondaryProducts(c *gin.Context) {
// 分页参数
page, _ := strconv.Atoi(c.DefaultQuery("page", "1"))
pageSize, _ := strconv.Atoi(c.DefaultQuery("page_size", "10"))
if page < 1 {
page = 1
}
if pageSize < 1 || pageSize > 100 {
pageSize = 10
}
// 搜索参数
sellerID := c.Query("seller_id")
productName := c.Query("product_name")
status := c.Query("status")
db := common.GetDB()
var products []models.SecondaryProduct
var total int64
// 构建查询条件
query := db.Model(&models.SecondaryProduct{}).Preload("Seller")
// 添加搜索条件
if sellerID != "" {
query = query.Where("seller_id = ?", sellerID)
}
if productName != "" {
query = query.Where("product_name LIKE ?", "%"+productName+"%")
}
if status != "" {
query = query.Where("status = ?", status)
}
// 获取总数
query.Count(&total)
// 分页查询
offset := (page - 1) * pageSize
err := query.Offset(offset).Limit(pageSize).Order("created_at DESC").Find(&products).Error
if err != nil {
c.JSON(http.StatusOK, common.Error(500, "查询二级商品列表失败"))
return
}
// 构建返回数据
result := map[string]interface{}{
"list": products,
"total": total,
"page": page,
"page_size": pageSize,
}
c.JSON(http.StatusOK, common.Success(result))
}
// GetProductStats 获取商品统计信息
func (h *AdminProductHandler) GetProductStats(c *gin.Context) {
db := common.GetDB()
stats := make(map[string]interface{})
// 一级商品统计
var totalPrimaryProducts int64
var onSalePrimaryProducts int64
db.Model(&models.PrimaryProduct{}).Count(&totalPrimaryProducts)
db.Model(&models.PrimaryProduct{}).Where("status = 1").Count(&onSalePrimaryProducts)
stats["total_primary_products"] = totalPrimaryProducts
stats["on_sale_primary_products"] = onSalePrimaryProducts
// 二级商品统计
var totalSecondaryProducts int64
var onSaleSecondaryProducts int64
db.Model(&models.SecondaryProduct{}).Count(&totalSecondaryProducts)
db.Model(&models.SecondaryProduct{}).Where("status = 1").Count(&onSaleSecondaryProducts)
stats["total_secondary_products"] = totalSecondaryProducts
stats["on_sale_secondary_products"] = onSaleSecondaryProducts
// 商品分类数量
var totalCategories int64
db.Model(&models.ProductCategory{}).Count(&totalCategories)
stats["total_categories"] = totalCategories
c.JSON(http.StatusOK, common.Success(stats))
}