init
This commit is contained in:
755
server/internal/handler/frontend.go
Normal file
755
server/internal/handler/frontend.go
Normal file
@@ -0,0 +1,755 @@
|
||||
package handler
|
||||
|
||||
import (
|
||||
"dianshang/internal/model"
|
||||
"dianshang/internal/service"
|
||||
"dianshang/pkg/response"
|
||||
"dianshang/pkg/utils"
|
||||
"fmt"
|
||||
"strconv"
|
||||
|
||||
"github.com/gin-gonic/gin"
|
||||
)
|
||||
|
||||
// FrontendHandler 前端接口处理器
|
||||
type FrontendHandler struct {
|
||||
productService *service.ProductService
|
||||
userService *service.UserService
|
||||
orderService *service.OrderService
|
||||
cartService *service.CartService
|
||||
bannerService *service.BannerService
|
||||
couponService *service.CouponService
|
||||
}
|
||||
|
||||
// NewFrontendHandler 创建前端接口处理器
|
||||
func NewFrontendHandler(
|
||||
productService *service.ProductService,
|
||||
userService *service.UserService,
|
||||
orderService *service.OrderService,
|
||||
cartService *service.CartService,
|
||||
bannerService *service.BannerService,
|
||||
couponService *service.CouponService,
|
||||
) *FrontendHandler {
|
||||
return &FrontendHandler{
|
||||
productService: productService,
|
||||
userService: userService,
|
||||
orderService: orderService,
|
||||
cartService: cartService,
|
||||
bannerService: bannerService,
|
||||
couponService: couponService,
|
||||
}
|
||||
}
|
||||
|
||||
// GetHomeData 获取首页数据
|
||||
func (h *FrontendHandler) GetHomeData(c *gin.Context) {
|
||||
// 获取轮播图
|
||||
banners, err := h.bannerService.GetActiveBanners()
|
||||
if err != nil {
|
||||
response.ErrorWithMessage(c, response.ERROR, "获取轮播图失败: "+err.Error())
|
||||
return
|
||||
}
|
||||
|
||||
// 获取分类
|
||||
categories, err := h.productService.GetCategories()
|
||||
if err != nil {
|
||||
response.ErrorWithMessage(c, response.ERROR, "获取分类失败: "+err.Error())
|
||||
return
|
||||
}
|
||||
|
||||
// 获取推荐商品
|
||||
recommendProducts, _, err := h.productService.GetProductList(1, 10, 0, "", 0, 0, "default", "desc")
|
||||
if err != nil {
|
||||
response.ErrorWithMessage(c, response.ERROR, "获取推荐商品失败: "+err.Error())
|
||||
return
|
||||
}
|
||||
|
||||
// 获取热门商品
|
||||
hotProducts, _, err := h.productService.GetProductList(1, 10, 0, "", 0, 0, "sales", "desc")
|
||||
if err != nil {
|
||||
response.ErrorWithMessage(c, response.ERROR, "获取热门商品失败: "+err.Error())
|
||||
return
|
||||
}
|
||||
|
||||
// 转换为前端格式
|
||||
frontendBanners := h.convertBannersToFrontend(banners)
|
||||
frontendCategories := h.convertCategoriesToFrontend(categories)
|
||||
frontendRecommendProducts := h.convertProductsToFrontend(recommendProducts)
|
||||
frontendHotProducts := h.convertProductsToFrontend(hotProducts)
|
||||
|
||||
homeData := gin.H{
|
||||
"banners": frontendBanners,
|
||||
"categories": frontendCategories,
|
||||
"recommendProducts": frontendRecommendProducts,
|
||||
"hotProducts": frontendHotProducts,
|
||||
}
|
||||
|
||||
response.Success(c, homeData)
|
||||
}
|
||||
|
||||
// GetProductsRecommend 获取推荐商品
|
||||
func (h *FrontendHandler) GetProductsRecommend(c *gin.Context) {
|
||||
page := utils.StringToInt(c.DefaultQuery("page", "1"))
|
||||
pageSize := utils.StringToInt(c.DefaultQuery("page_size", "10"))
|
||||
|
||||
products, pagination, err := h.productService.GetProductList(page, pageSize, 0, "", 0, 0, "default", "desc")
|
||||
if err != nil {
|
||||
response.ErrorWithMessage(c, response.ERROR, err.Error())
|
||||
return
|
||||
}
|
||||
|
||||
frontendProducts := h.convertProductsToFrontend(products)
|
||||
response.Page(c, frontendProducts, pagination.Total, pagination.Page, pagination.PageSize)
|
||||
}
|
||||
|
||||
// GetProductsHot 获取热门商品
|
||||
func (h *FrontendHandler) GetProductsHot(c *gin.Context) {
|
||||
page := utils.StringToInt(c.DefaultQuery("page", "1"))
|
||||
pageSize := utils.StringToInt(c.DefaultQuery("page_size", "10"))
|
||||
|
||||
products, pagination, err := h.productService.GetProductList(page, pageSize, 0, "", 0, 0, "sales", "desc")
|
||||
if err != nil {
|
||||
response.ErrorWithMessage(c, response.ERROR, err.Error())
|
||||
return
|
||||
}
|
||||
|
||||
frontendProducts := h.convertProductsToFrontend(products)
|
||||
response.Page(c, frontendProducts, pagination.Total, pagination.Page, pagination.PageSize)
|
||||
}
|
||||
|
||||
// GetProductDetail 获取商品详情
|
||||
func (h *FrontendHandler) GetProductDetail(c *gin.Context) {
|
||||
spuID := c.Param("spuId")
|
||||
if spuID == "" {
|
||||
response.BadRequest(c, "商品ID不能为空")
|
||||
return
|
||||
}
|
||||
|
||||
// 这里简化处理,实际应该根据spuID查询
|
||||
id := utils.StringToUint(spuID)
|
||||
if id == 0 {
|
||||
response.BadRequest(c, "无效的商品ID")
|
||||
return
|
||||
}
|
||||
|
||||
product, err := h.productService.GetProductDetail(id)
|
||||
if err != nil {
|
||||
response.ErrorWithMessage(c, response.ERROR, err.Error())
|
||||
return
|
||||
}
|
||||
|
||||
frontendProduct := h.convertProductToFrontend(product)
|
||||
response.Success(c, frontendProduct)
|
||||
}
|
||||
|
||||
// GetUserCenter 获取用户中心数据
|
||||
func (h *FrontendHandler) GetUserCenter(c *gin.Context) {
|
||||
userID := c.GetUint("user_id")
|
||||
if userID == 0 {
|
||||
response.Unauthorized(c)
|
||||
return
|
||||
}
|
||||
|
||||
user, err := h.userService.GetUserByID(userID)
|
||||
if err != nil {
|
||||
response.ErrorWithMessage(c, response.ERROR, err.Error())
|
||||
return
|
||||
}
|
||||
|
||||
// 获取用户优惠券数量
|
||||
couponCount := 0
|
||||
if userCoupons, err := h.couponService.GetUserCoupons(userID, 1); err == nil { // 状态1表示未使用
|
||||
couponCount = len(userCoupons)
|
||||
}
|
||||
|
||||
|
||||
|
||||
// 获取用户订单统计
|
||||
orderStats := map[int]int{
|
||||
1: 0, // 待付款 (对应前端status=1)
|
||||
3: 0, // 待发货 (对应前端status=3)
|
||||
5: 0, // 待收货 (对应前端status=5)
|
||||
6: 0, // 待评价 (对应前端status=6)
|
||||
}
|
||||
|
||||
// 获取用户订单列表来统计各状态订单数量
|
||||
if orders, _, err := h.orderService.GetUserOrders(userID, 0, 1, 1000); err == nil {
|
||||
for _, order := range orders {
|
||||
switch order.Status {
|
||||
case 1: // 数据库中的待付款状态
|
||||
orderStats[1]++ // 映射到前端status=1
|
||||
case 2: // 数据库中的待发货状态
|
||||
orderStats[3]++ // 映射到前端status=3
|
||||
case 3: // 数据库中的待收货状态
|
||||
orderStats[5]++ // 映射到前端status=5
|
||||
case 4: // 数据库中的待评价状态
|
||||
orderStats[6]++ // 映射到前端status=6
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// 构造用户中心数据
|
||||
userCenter := model.FrontendUserCenter{
|
||||
UserInfo: model.FrontendUserInfo{
|
||||
AvatarURL: user.Avatar,
|
||||
NickName: user.Nickname,
|
||||
PhoneNumber: user.Phone,
|
||||
Gender: int(user.Gender),
|
||||
},
|
||||
CountsData: []model.FrontendCountData{
|
||||
{Num: couponCount, Name: "优惠券", Type: "coupon"},
|
||||
{Num: 0, Name: "收藏", Type: "favorite"},
|
||||
},
|
||||
OrderTagInfos: []model.FrontendOrderTagInfo{
|
||||
{OrderNum: orderStats[1], TabType: 1}, // 待付款
|
||||
{OrderNum: orderStats[3], TabType: 3}, // 待发货
|
||||
{OrderNum: orderStats[5], TabType: 5}, // 待收货
|
||||
{OrderNum: orderStats[6], TabType: 6}, // 待评价
|
||||
},
|
||||
CustomerServiceInfo: model.FrontendCustomerServiceInfo{
|
||||
ServicePhone: "400-123-4567",
|
||||
ServiceTimeDuration: "9:00-18:00",
|
||||
},
|
||||
}
|
||||
|
||||
response.Success(c, userCenter)
|
||||
}
|
||||
|
||||
// GetCartData 获取购物车数据
|
||||
func (h *FrontendHandler) GetCartData(c *gin.Context) {
|
||||
userID := c.GetUint("user_id")
|
||||
if userID == 0 {
|
||||
response.Unauthorized(c)
|
||||
return
|
||||
}
|
||||
|
||||
cartItems, err := h.cartService.GetCart(userID)
|
||||
if err != nil {
|
||||
response.ErrorWithMessage(c, response.ERROR, err.Error())
|
||||
return
|
||||
}
|
||||
|
||||
frontendCartData := h.convertCartToFrontend(cartItems)
|
||||
response.Success(c, frontendCartData)
|
||||
}
|
||||
|
||||
// GetOrderList 获取订单列表
|
||||
func (h *FrontendHandler) GetOrderList(c *gin.Context) {
|
||||
userID := c.GetUint("user_id")
|
||||
if userID == 0 {
|
||||
response.Unauthorized(c)
|
||||
return
|
||||
}
|
||||
|
||||
page := utils.StringToInt(c.DefaultQuery("page", "1"))
|
||||
pageSize := utils.StringToInt(c.DefaultQuery("page_size", "10"))
|
||||
statusStr := c.Query("status")
|
||||
status := 0
|
||||
if statusStr != "" {
|
||||
frontendStatus := utils.StringToInt(statusStr)
|
||||
// 将前端状态映射到数据库状态
|
||||
// 前端和数据库状态保持一致:
|
||||
// 1=未付款, 2=已付款/待发货, 3=待发货, 4=已发货, 5=待收货, 6=已完成, 7=已取消, 8=退货中, 9=已退款
|
||||
status = frontendStatus
|
||||
}
|
||||
|
||||
orders, pagination, err := h.orderService.GetUserOrders(userID, status, page, pageSize)
|
||||
if err != nil {
|
||||
response.ErrorWithMessage(c, response.ERROR, err.Error())
|
||||
return
|
||||
}
|
||||
|
||||
frontendOrders := h.convertOrdersToFrontend(orders)
|
||||
orderList := model.FrontendOrderList{
|
||||
PageNum: pagination.Page,
|
||||
PageSize: pagination.PageSize,
|
||||
TotalCount: int(pagination.Total),
|
||||
Orders: frontendOrders,
|
||||
}
|
||||
|
||||
response.Success(c, orderList)
|
||||
}
|
||||
|
||||
// GetAddressList 获取地址列表
|
||||
func (h *FrontendHandler) GetAddressList(c *gin.Context) {
|
||||
userID := c.GetUint("user_id")
|
||||
if userID == 0 {
|
||||
response.Unauthorized(c)
|
||||
return
|
||||
}
|
||||
|
||||
addresses, err := h.userService.GetUserAddresses(userID)
|
||||
if err != nil {
|
||||
response.ErrorWithMessage(c, response.ERROR, err.Error())
|
||||
return
|
||||
}
|
||||
|
||||
frontendAddresses := h.convertAddressesToFrontend(addresses)
|
||||
response.Success(c, frontendAddresses)
|
||||
}
|
||||
|
||||
// 转换函数
|
||||
|
||||
func (h *FrontendHandler) convertBannersToFrontend(banners []model.Banner) []gin.H {
|
||||
result := make([]gin.H, len(banners))
|
||||
for i, banner := range banners {
|
||||
result[i] = gin.H{
|
||||
"img": banner.Image,
|
||||
"text": banner.Title,
|
||||
"url": banner.LinkValue,
|
||||
}
|
||||
}
|
||||
return result
|
||||
}
|
||||
|
||||
func (h *FrontendHandler) convertCategoriesToFrontend(categories []model.Category) []model.FrontendCategory {
|
||||
result := make([]model.FrontendCategory, len(categories))
|
||||
for i, category := range categories {
|
||||
frontendCategory := model.FrontendCategory{
|
||||
GroupID: strconv.Itoa(int(category.ID)),
|
||||
Name: category.Name,
|
||||
Thumbnail: category.Icon,
|
||||
}
|
||||
|
||||
// 处理子分类
|
||||
if len(category.Children) > 0 {
|
||||
frontendCategory.Children = h.convertCategoriesToFrontend(category.Children)
|
||||
}
|
||||
|
||||
result[i] = frontendCategory
|
||||
}
|
||||
return result
|
||||
}
|
||||
|
||||
func (h *FrontendHandler) convertProductsToFrontend(products []model.Product) []model.FrontendProduct {
|
||||
result := make([]model.FrontendProduct, len(products))
|
||||
for i, product := range products {
|
||||
result[i] = h.convertProductToFrontend(&product)
|
||||
}
|
||||
return result
|
||||
}
|
||||
|
||||
func (h *FrontendHandler) convertProductToFrontend(product *model.Product) model.FrontendProduct {
|
||||
// 获取商品图片
|
||||
images := make([]string, 0)
|
||||
if len(product.Images) > 0 {
|
||||
for _, img := range product.Images {
|
||||
images = append(images, img)
|
||||
}
|
||||
}
|
||||
|
||||
// 若无图片则回退使用主图,确保前端轮播可显示
|
||||
if len(images) == 0 && product.MainImage != "" {
|
||||
images = append(images, product.MainImage)
|
||||
}
|
||||
|
||||
// 生成详情描述,优先使用详情图片数组,其次文本描述
|
||||
desc := make([]string, 0)
|
||||
if len(product.DetailImages) > 0 {
|
||||
for _, d := range product.DetailImages {
|
||||
desc = append(desc, d)
|
||||
}
|
||||
} else if product.Description != "" {
|
||||
desc = append(desc, product.Description)
|
||||
}
|
||||
|
||||
// 获取商品规格和SKU
|
||||
specList := make([]model.FrontendProductSpec, 0)
|
||||
skuList := make([]model.FrontendProductSKU, 0)
|
||||
|
||||
// 用于收集所有规格信息
|
||||
specMap := make(map[string]map[string]bool) // specName -> specValue -> exists
|
||||
|
||||
if len(product.SKUs) > 0 {
|
||||
// 首先遍历所有SKU,收集规格信息
|
||||
for _, sku := range product.SKUs {
|
||||
for specName, specValue := range sku.SpecValues {
|
||||
if specMap[specName] == nil {
|
||||
specMap[specName] = make(map[string]bool)
|
||||
}
|
||||
if specValueStr, ok := specValue.(string); ok {
|
||||
specMap[specName][specValueStr] = true
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// 生成specList和规格值ID映射
|
||||
specIndex := 1
|
||||
specNameToID := make(map[string]string)
|
||||
specValueToID := make(map[string]map[string]string) // specName -> specValue -> specValueID
|
||||
for specName, specValues := range specMap {
|
||||
specID := strconv.Itoa(specIndex)
|
||||
specNameToID[specName] = specID
|
||||
specValueToID[specName] = make(map[string]string)
|
||||
|
||||
specValueList := make([]model.FrontendProductSpecValue, 0)
|
||||
valueIndex := 1
|
||||
for specValue := range specValues {
|
||||
specValueID := fmt.Sprintf("%s_%d", specID, valueIndex)
|
||||
specValueToID[specName][specValue] = specValueID
|
||||
|
||||
specValueList = append(specValueList, model.FrontendProductSpecValue{
|
||||
SpecValueID: specValueID,
|
||||
SpecID: specID,
|
||||
SaasID: "default",
|
||||
SpecValue: specValue,
|
||||
Image: "",
|
||||
})
|
||||
valueIndex++
|
||||
}
|
||||
|
||||
specList = append(specList, model.FrontendProductSpec{
|
||||
SpecID: specID,
|
||||
Title: specName,
|
||||
SpecValueList: specValueList,
|
||||
})
|
||||
specIndex++
|
||||
}
|
||||
|
||||
// 生成skuList
|
||||
for _, sku := range product.SKUs {
|
||||
specInfo := make([]model.FrontendSKUSpecInfo, 0)
|
||||
for specName, specValue := range sku.SpecValues {
|
||||
if specValueStr, ok := specValue.(string); ok {
|
||||
specValueID := ""
|
||||
if specValueMap, exists := specValueToID[specName]; exists {
|
||||
if valueID, exists := specValueMap[specValueStr]; exists {
|
||||
specValueID = valueID
|
||||
}
|
||||
}
|
||||
|
||||
specInfo = append(specInfo, model.FrontendSKUSpecInfo{
|
||||
SpecID: specNameToID[specName],
|
||||
SpecTitle: specName,
|
||||
SpecValueID: specValueID,
|
||||
SpecValue: specValueStr,
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
frontendSKU := model.FrontendProductSKU{
|
||||
SkuID: strconv.Itoa(int(sku.ID)),
|
||||
SkuImage: sku.Image,
|
||||
SpecInfo: specInfo,
|
||||
PriceInfo: []model.FrontendSKUPriceInfo{
|
||||
{
|
||||
PriceType: 1,
|
||||
Price: fmt.Sprintf("%.0f", sku.Price),
|
||||
PriceTypeName: "销售价",
|
||||
},
|
||||
},
|
||||
StockInfo: model.FrontendSKUStockInfo{
|
||||
StockQuantity: sku.Stock,
|
||||
SafeStockQuantity: 10,
|
||||
SoldQuantity: 0,
|
||||
},
|
||||
}
|
||||
skuList = append(skuList, frontendSKU)
|
||||
}
|
||||
}
|
||||
|
||||
// 获取商品标签
|
||||
spuTagList := make([]model.FrontendProductTag, 0)
|
||||
if len(product.Tags) > 0 {
|
||||
for _, tag := range product.Tags {
|
||||
spuTagList = append(spuTagList, model.FrontendProductTag{
|
||||
ID: strconv.Itoa(int(tag.ID)),
|
||||
Title: tag.Name,
|
||||
Image: "",
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
return model.FrontendProduct{
|
||||
SaasID: "default",
|
||||
StoreID: strconv.Itoa(int(product.StoreID)),
|
||||
SpuID: strconv.Itoa(int(product.ID)),
|
||||
Title: product.Name,
|
||||
PrimaryImage: product.MainImage,
|
||||
Images: images,
|
||||
Available: 1,
|
||||
MinSalePrice: fmt.Sprintf("%.0f", product.Price),
|
||||
MinLinePrice: fmt.Sprintf("%.0f", product.Price),
|
||||
MaxSalePrice: fmt.Sprintf("%.0f", product.Price),
|
||||
MaxLinePrice: fmt.Sprintf("%.0f", product.Price),
|
||||
SpuStockQuantity: product.Stock,
|
||||
SoldNum: product.Sales,
|
||||
IsPutOnSale: 1,
|
||||
CategoryIds: []string{strconv.Itoa(int(product.CategoryID))},
|
||||
SpecList: specList,
|
||||
SkuList: skuList,
|
||||
SpuTagList: spuTagList,
|
||||
Desc: desc,
|
||||
Video: func() *string { if product.VideoURL != "" { v := product.VideoURL; return &v }; return nil }(),
|
||||
Etitle: product.Name,
|
||||
PromotionList: nil,
|
||||
MinProfitPrice: nil,
|
||||
}
|
||||
}
|
||||
|
||||
func (h *FrontendHandler) convertCartToFrontend(cartItems []model.Cart) model.FrontendCartData {
|
||||
if len(cartItems) == 0 {
|
||||
return model.FrontendCartData{
|
||||
IsNotEmpty: false,
|
||||
StoreGoods: []model.FrontendStoreGoods{},
|
||||
IsAllSelected: false,
|
||||
SelectedGoodsCount: 0,
|
||||
TotalAmount: "0.00",
|
||||
TotalDiscountAmount: "0.00",
|
||||
}
|
||||
}
|
||||
|
||||
// 按店铺分组
|
||||
storeMap := make(map[uint][]model.Cart)
|
||||
for _, item := range cartItems {
|
||||
storeID := item.Product.StoreID
|
||||
storeMap[storeID] = append(storeMap[storeID], item)
|
||||
}
|
||||
|
||||
storeGoods := make([]model.FrontendStoreGoods, 0)
|
||||
totalAmount := 0.0
|
||||
selectedCount := 0
|
||||
|
||||
for storeID, items := range storeMap {
|
||||
goodsList := make([]model.FrontendCartGoods, 0)
|
||||
storeTotal := 0.0
|
||||
|
||||
for _, item := range items {
|
||||
price := (item.Product.Price / 100) * float64(item.Quantity)
|
||||
storeTotal += price
|
||||
if item.Selected {
|
||||
selectedCount += item.Quantity
|
||||
totalAmount += price
|
||||
}
|
||||
|
||||
// 构建SKU规格信息
|
||||
specInfo := make([]model.FrontendSpecification, 0)
|
||||
if item.SKUID != nil {
|
||||
// 获取对应的SKU信息
|
||||
for _, sku := range item.Product.SKUs {
|
||||
if sku.ID == *item.SKUID {
|
||||
for specName, specValue := range sku.SpecValues {
|
||||
if specValueStr, ok := specValue.(string); ok {
|
||||
specInfo = append(specInfo, model.FrontendSpecification{
|
||||
SpecTitle: specName,
|
||||
SpecValue: specValueStr,
|
||||
})
|
||||
}
|
||||
}
|
||||
break
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
goodsList = append(goodsList, model.FrontendCartGoods{
|
||||
UID: strconv.Itoa(int(item.ID)),
|
||||
SaasID: "default",
|
||||
StoreID: strconv.Itoa(int(storeID)),
|
||||
SpuID: strconv.Itoa(int(item.ProductID)),
|
||||
SkuID: func() string {
|
||||
if item.SKUID != nil {
|
||||
return strconv.Itoa(int(*item.SKUID))
|
||||
}
|
||||
return "0"
|
||||
}(),
|
||||
IsSelected: utils.BoolToInt(item.Selected),
|
||||
Thumb: item.Product.MainImage,
|
||||
Title: item.Product.Name,
|
||||
PrimaryImage: item.Product.MainImage,
|
||||
SpecInfo: specInfo,
|
||||
Quantity: item.Quantity,
|
||||
StockStatus: item.Product.Stock > 0,
|
||||
StockQuantity: item.Product.Stock,
|
||||
Price: fmt.Sprintf("%.0f", item.Product.Price),
|
||||
OriginPrice: fmt.Sprintf("%.0f", item.Product.Price),
|
||||
JoinCartTime: item.CreatedAt.Format("2006-01-02 15:04:05"),
|
||||
Available: 1,
|
||||
PutOnSale: 1,
|
||||
})
|
||||
}
|
||||
|
||||
// 动态获取店铺名称
|
||||
storeName := "默认店铺" // 默认店铺名
|
||||
if storeID > 0 {
|
||||
store, err := h.productService.GetStoreByID(storeID)
|
||||
if err == nil && store != nil {
|
||||
storeName = store.Name
|
||||
}
|
||||
}
|
||||
|
||||
storeGoods = append(storeGoods, model.FrontendStoreGoods{
|
||||
StoreID: strconv.Itoa(int(storeID)),
|
||||
StoreName: storeName,
|
||||
StoreStatus: 1,
|
||||
TotalDiscountSalePrice: fmt.Sprintf("%.0f", storeTotal),
|
||||
GoodsList: goodsList,
|
||||
})
|
||||
}
|
||||
|
||||
return model.FrontendCartData{
|
||||
IsNotEmpty: len(cartItems) > 0,
|
||||
StoreGoods: storeGoods,
|
||||
IsAllSelected: selectedCount == len(cartItems),
|
||||
SelectedGoodsCount: selectedCount,
|
||||
TotalAmount: fmt.Sprintf("%.0f", totalAmount),
|
||||
TotalDiscountAmount: "0",
|
||||
}
|
||||
}
|
||||
|
||||
func (h *FrontendHandler) convertOrdersToFrontend(orders []model.Order) []model.FrontendOrder {
|
||||
result := make([]model.FrontendOrder, len(orders))
|
||||
for i, order := range orders {
|
||||
orderItems := make([]model.FrontendOrderItem, len(order.OrderItems))
|
||||
for j, item := range order.OrderItems {
|
||||
// 处理规格信息
|
||||
specifications := []model.FrontendSpecification{}
|
||||
|
||||
// 优先从SKU获取规格信息
|
||||
if item.SKUID != nil && item.SKU.ID > 0 && len(item.SKU.SpecValues) > 0 {
|
||||
for specName, specValue := range item.SKU.SpecValues {
|
||||
if specValueStr, ok := specValue.(string); ok {
|
||||
specifications = append(specifications, model.FrontendSpecification{
|
||||
SpecTitle: specName,
|
||||
SpecValue: specValueStr,
|
||||
})
|
||||
}
|
||||
}
|
||||
} else if len(item.SpecInfo) > 0 {
|
||||
// 如果SKU没有规格信息,从订单项的SpecInfo获取
|
||||
for specName, specValue := range item.SpecInfo {
|
||||
if specValueStr, ok := specValue.(string); ok {
|
||||
specifications = append(specifications, model.FrontendSpecification{
|
||||
SpecTitle: specName,
|
||||
SpecValue: specValueStr,
|
||||
})
|
||||
}
|
||||
}
|
||||
} else if item.SpecName != "" && item.SpecValue != "" {
|
||||
// 从单独的规格字段获取
|
||||
specifications = append(specifications, model.FrontendSpecification{
|
||||
SpecTitle: item.SpecName,
|
||||
SpecValue: item.SpecValue,
|
||||
})
|
||||
} else {
|
||||
// 如果订单项没有规格信息,尝试从产品的第一个SKU获取默认规格
|
||||
if item.Product.ID > 0 && len(item.Product.SKUs) > 0 {
|
||||
firstSKU := item.Product.SKUs[0]
|
||||
for specName, specValue := range firstSKU.SpecValues {
|
||||
if specValueStr, ok := specValue.(string); ok {
|
||||
specifications = append(specifications, model.FrontendSpecification{
|
||||
SpecTitle: specName,
|
||||
SpecValue: specValueStr, // 使用实际的规格值
|
||||
})
|
||||
}
|
||||
}
|
||||
}
|
||||
// 如果还是没有规格信息,提供一个默认的规格
|
||||
if len(specifications) == 0 {
|
||||
specifications = append(specifications, model.FrontendSpecification{
|
||||
SpecTitle: "规格",
|
||||
SpecValue: "标准",
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
orderItems[j] = model.FrontendOrderItem{
|
||||
ID: strconv.Itoa(int(item.ID)),
|
||||
SpuID: strconv.Itoa(int(item.ProductID)),
|
||||
SkuID: func() string {
|
||||
if item.SKUID != nil {
|
||||
return strconv.Itoa(int(*item.SKUID))
|
||||
}
|
||||
return "0"
|
||||
}(),
|
||||
GoodsMainType: 1,
|
||||
GoodsViceType: 1,
|
||||
GoodsName: item.ProductName,
|
||||
Specifications: specifications,
|
||||
GoodsPictureURL: item.ProductImage,
|
||||
OriginPrice: fmt.Sprintf("%.0f", item.Price),
|
||||
ActualPrice: fmt.Sprintf("%.0f", item.Price),
|
||||
BuyQuantity: item.Quantity,
|
||||
ItemTotalAmount: fmt.Sprintf("%.0f", item.Price*float64(item.Quantity)),
|
||||
ItemDiscountAmount: "0.00",
|
||||
ItemPaymentAmount: fmt.Sprintf("%.0f", item.Price*float64(item.Quantity)),
|
||||
GoodsPaymentPrice: fmt.Sprintf("%.0f", item.Price),
|
||||
}
|
||||
}
|
||||
|
||||
// 动态获取店铺名称
|
||||
storeName := "默认店铺" // 默认店铺名
|
||||
if order.StoreID > 0 {
|
||||
store, err := h.productService.GetStoreByID(order.StoreID)
|
||||
if err == nil && store != nil {
|
||||
storeName = store.Name
|
||||
}
|
||||
}
|
||||
|
||||
result[i] = model.FrontendOrder{
|
||||
SaasID: "default",
|
||||
StoreID: strconv.Itoa(int(order.StoreID)),
|
||||
StoreName: storeName,
|
||||
UID: strconv.Itoa(int(order.UserID)),
|
||||
ParentOrderNo: order.OrderNo,
|
||||
OrderID: strconv.Itoa(int(order.ID)),
|
||||
OrderNo: order.OrderNo,
|
||||
OrderType: 1,
|
||||
OrderSubType: 1,
|
||||
OrderStatus: int(order.Status),
|
||||
TotalAmount: fmt.Sprintf("%.0f", order.TotalAmount),
|
||||
GoodsAmount: fmt.Sprintf("%.0f", order.TotalAmount),
|
||||
GoodsAmountApp: fmt.Sprintf("%.0f", order.TotalAmount),
|
||||
PaymentAmount: fmt.Sprintf("%.0f", order.PayAmount),
|
||||
FreightFee: fmt.Sprintf("%.0f", order.ShippingFee),
|
||||
PackageFee: "0",
|
||||
DiscountAmount: fmt.Sprintf("%.0f", order.DiscountAmount),
|
||||
ChannelType: 1,
|
||||
ChannelSource: "miniprogram",
|
||||
ChannelIdentity: "wechat",
|
||||
Remark: order.Remark,
|
||||
CreateTime: order.CreatedAt.Format("2006-01-02 15:04:05"),
|
||||
OrderItemVOs: orderItems,
|
||||
LogisticsVO: model.FrontendLogistics{
|
||||
LogisticsType: 1,
|
||||
LogisticsNo: order.LogisticsNo,
|
||||
LogisticsCompanyCode: "SF",
|
||||
LogisticsCompanyName: "顺丰速运",
|
||||
ReceiverName: order.ReceiverName,
|
||||
ReceiverPhone: order.ReceiverPhone,
|
||||
ReceiverAddress: order.ReceiverAddress,
|
||||
},
|
||||
PaymentVO: model.FrontendPayment{
|
||||
PayStatus: int(order.PayStatus),
|
||||
Amount: fmt.Sprintf("%.2f", order.PayAmount),
|
||||
},
|
||||
}
|
||||
}
|
||||
return result
|
||||
}
|
||||
|
||||
func (h *FrontendHandler) convertAddressesToFrontend(addresses []model.UserAddress) []model.FrontendAddress {
|
||||
result := make([]model.FrontendAddress, len(addresses))
|
||||
for i, addr := range addresses {
|
||||
result[i] = model.FrontendAddress{
|
||||
SaasID: "default",
|
||||
UID: strconv.Itoa(int(addr.UserID)),
|
||||
ID: strconv.Itoa(int(addr.ID)),
|
||||
AddressID: strconv.Itoa(int(addr.ID)),
|
||||
Phone: addr.Phone,
|
||||
Name: addr.Name,
|
||||
CountryName: "中国",
|
||||
CountryCode: "CN",
|
||||
ProvinceName: addr.ProvinceName,
|
||||
ProvinceCode: "000000", // UserAddress模型中没有ProvinceCode字段,使用默认值
|
||||
CityName: addr.CityName,
|
||||
CityCode: "000000", // UserAddress模型中没有CityCode字段,使用默认值
|
||||
DistrictName: addr.DistrictName,
|
||||
DistrictCode: "000000", // UserAddress模型中没有DistrictCode字段,使用默认值
|
||||
DetailAddress: addr.DetailAddress,
|
||||
IsDefault: utils.BoolToInt(addr.IsDefault),
|
||||
AddressTag: addr.AddressTag,
|
||||
Latitude: fmt.Sprintf("%.6f", addr.Latitude),
|
||||
Longitude: fmt.Sprintf("%.6f", addr.Longitude),
|
||||
}
|
||||
}
|
||||
return result
|
||||
}
|
||||
Reference in New Issue
Block a user