f
This commit is contained in:
@@ -47,4 +47,7 @@ type ProductApplicationService interface {
|
||||
CreateProductApiConfig(ctx context.Context, productID string, config *responses.ProductApiConfigResponse) error
|
||||
UpdateProductApiConfig(ctx context.Context, configID string, config *responses.ProductApiConfigResponse) error
|
||||
DeleteProductApiConfig(ctx context.Context, configID string) error
|
||||
|
||||
// 产品字典导出
|
||||
ExportProductDictionary(ctx context.Context, format string) ([]byte, error)
|
||||
}
|
||||
|
||||
@@ -16,6 +16,7 @@ import (
|
||||
api_services "tyapi-server/internal/domains/api/services"
|
||||
"tyapi-server/internal/domains/product/entities"
|
||||
product_service "tyapi-server/internal/domains/product/services"
|
||||
"tyapi-server/internal/shared/export"
|
||||
"tyapi-server/internal/shared/interfaces"
|
||||
)
|
||||
|
||||
@@ -28,6 +29,7 @@ type ProductApplicationServiceImpl struct {
|
||||
documentationAppService DocumentationApplicationServiceInterface
|
||||
formConfigService api_services.FormConfigService
|
||||
logger *zap.Logger
|
||||
exportManager *export.ExportManager
|
||||
}
|
||||
|
||||
// NewProductApplicationService 创建产品应用服务
|
||||
@@ -38,6 +40,7 @@ func NewProductApplicationService(
|
||||
documentationAppService DocumentationApplicationServiceInterface,
|
||||
formConfigService api_services.FormConfigService,
|
||||
logger *zap.Logger,
|
||||
exportManager *export.ExportManager,
|
||||
) ProductApplicationService {
|
||||
return &ProductApplicationServiceImpl{
|
||||
productManagementService: productManagementService,
|
||||
@@ -46,6 +49,7 @@ func NewProductApplicationService(
|
||||
documentationAppService: documentationAppService,
|
||||
formConfigService: formConfigService,
|
||||
logger: logger,
|
||||
exportManager: exportManager,
|
||||
}
|
||||
}
|
||||
|
||||
@@ -492,24 +496,24 @@ func (s *ProductApplicationServiceImpl) GetProductByIDForUser(ctx context.Contex
|
||||
// convertToProductInfoResponse 转换为产品信息响应
|
||||
func (s *ProductApplicationServiceImpl) convertToProductInfoResponse(product *entities.Product) *responses.ProductInfoResponse {
|
||||
response := &responses.ProductInfoResponse{
|
||||
ID: product.ID,
|
||||
OldID: product.OldID,
|
||||
Name: product.Name,
|
||||
Code: product.Code,
|
||||
Description: product.Description,
|
||||
Content: product.Content,
|
||||
CategoryID: product.CategoryID,
|
||||
SubCategoryID: product.SubCategoryID,
|
||||
Price: product.Price.InexactFloat64(),
|
||||
IsEnabled: product.IsEnabled,
|
||||
IsPackage: product.IsPackage,
|
||||
SellUIComponent: product.SellUIComponent,
|
||||
ID: product.ID,
|
||||
OldID: product.OldID,
|
||||
Name: product.Name,
|
||||
Code: product.Code,
|
||||
Description: product.Description,
|
||||
Content: product.Content,
|
||||
CategoryID: product.CategoryID,
|
||||
SubCategoryID: product.SubCategoryID,
|
||||
Price: product.Price.InexactFloat64(),
|
||||
IsEnabled: product.IsEnabled,
|
||||
IsPackage: product.IsPackage,
|
||||
SellUIComponent: product.SellUIComponent,
|
||||
UIComponentPrice: product.UIComponentPrice.InexactFloat64(),
|
||||
SEOTitle: product.SEOTitle,
|
||||
SEODescription: product.SEODescription,
|
||||
SEOKeywords: product.SEOKeywords,
|
||||
CreatedAt: product.CreatedAt,
|
||||
UpdatedAt: product.UpdatedAt,
|
||||
SEOTitle: product.SEOTitle,
|
||||
SEODescription: product.SEODescription,
|
||||
SEOKeywords: product.SEOKeywords,
|
||||
CreatedAt: product.CreatedAt,
|
||||
UpdatedAt: product.UpdatedAt,
|
||||
}
|
||||
|
||||
// 添加一级分类信息
|
||||
@@ -544,27 +548,27 @@ func (s *ProductApplicationServiceImpl) convertToProductInfoResponse(product *en
|
||||
// convertToProductAdminInfoResponse 转换为管理员产品信息响应
|
||||
func (s *ProductApplicationServiceImpl) convertToProductAdminInfoResponse(product *entities.Product) *responses.ProductAdminInfoResponse {
|
||||
response := &responses.ProductAdminInfoResponse{
|
||||
ID: product.ID,
|
||||
OldID: product.OldID,
|
||||
Name: product.Name,
|
||||
Code: product.Code,
|
||||
Description: product.Description,
|
||||
Content: product.Content,
|
||||
CategoryID: product.CategoryID,
|
||||
SubCategoryID: product.SubCategoryID,
|
||||
Price: product.Price.InexactFloat64(),
|
||||
CostPrice: product.CostPrice.InexactFloat64(),
|
||||
Remark: product.Remark,
|
||||
IsEnabled: product.IsEnabled,
|
||||
IsVisible: product.IsVisible, // 管理员可以看到可见状态
|
||||
IsPackage: product.IsPackage,
|
||||
SellUIComponent: product.SellUIComponent,
|
||||
ID: product.ID,
|
||||
OldID: product.OldID,
|
||||
Name: product.Name,
|
||||
Code: product.Code,
|
||||
Description: product.Description,
|
||||
Content: product.Content,
|
||||
CategoryID: product.CategoryID,
|
||||
SubCategoryID: product.SubCategoryID,
|
||||
Price: product.Price.InexactFloat64(),
|
||||
CostPrice: product.CostPrice.InexactFloat64(),
|
||||
Remark: product.Remark,
|
||||
IsEnabled: product.IsEnabled,
|
||||
IsVisible: product.IsVisible, // 管理员可以看到可见状态
|
||||
IsPackage: product.IsPackage,
|
||||
SellUIComponent: product.SellUIComponent,
|
||||
UIComponentPrice: product.UIComponentPrice.InexactFloat64(),
|
||||
SEOTitle: product.SEOTitle,
|
||||
SEODescription: product.SEODescription,
|
||||
SEOKeywords: product.SEOKeywords,
|
||||
CreatedAt: product.CreatedAt,
|
||||
UpdatedAt: product.UpdatedAt,
|
||||
SEOTitle: product.SEOTitle,
|
||||
SEODescription: product.SEODescription,
|
||||
SEOKeywords: product.SEOKeywords,
|
||||
CreatedAt: product.CreatedAt,
|
||||
UpdatedAt: product.UpdatedAt,
|
||||
}
|
||||
|
||||
// 添加一级分类信息
|
||||
@@ -994,103 +998,103 @@ func (s *ProductApplicationServiceImpl) mergeRequestParamsFromDTOs(ctx context.C
|
||||
// getDTOMap 获取API代码到DTO结构体的映射(复用form_config_service的逻辑)
|
||||
func (s *ProductApplicationServiceImpl) getDTOMap() map[string]interface{} {
|
||||
return map[string]interface{}{
|
||||
"IVYZ9363": &dto.IVYZ9363Req{},
|
||||
"IVYZ385E": &dto.IVYZ385EReq{},
|
||||
"IVYZ5733": &dto.IVYZ5733Req{},
|
||||
"FLXG3D56": &dto.FLXG3D56Req{},
|
||||
"FLXG75FE": &dto.FLXG75FEReq{},
|
||||
"FLXG0V3B": &dto.FLXG0V3BReq{},
|
||||
"FLXG0V4B": &dto.FLXG0V4BReq{},
|
||||
"FLXG54F5": &dto.FLXG54F5Req{},
|
||||
"FLXG162A": &dto.FLXG162AReq{},
|
||||
"FLXG0687": &dto.FLXG0687Req{},
|
||||
"FLXGBC21": &dto.FLXGBC21Req{},
|
||||
"FLXG970F": &dto.FLXG970FReq{},
|
||||
"FLXG5876": &dto.FLXG5876Req{},
|
||||
"FLXG9687": &dto.FLXG9687Req{},
|
||||
"FLXGC9D1": &dto.FLXGC9D1Req{},
|
||||
"FLXGCA3D": &dto.FLXGCA3DReq{},
|
||||
"FLXGDEC7": &dto.FLXGDEC7Req{},
|
||||
"JRZQ0A03": &dto.JRZQ0A03Req{},
|
||||
"JRZQ4AA8": &dto.JRZQ4AA8Req{},
|
||||
"JRZQ8203": &dto.JRZQ8203Req{},
|
||||
"JRZQDCBE": &dto.JRZQDCBEReq{},
|
||||
"QYGL2ACD": &dto.QYGL2ACDReq{},
|
||||
"QYGL6F2D": &dto.QYGL6F2DReq{},
|
||||
"QYGL45BD": &dto.QYGL45BDReq{},
|
||||
"QYGL8261": &dto.QYGL8261Req{},
|
||||
"QYGL8271": &dto.QYGL8271Req{},
|
||||
"QYGLB4C0": &dto.QYGLB4C0Req{},
|
||||
"QYGL23T7": &dto.QYGL23T7Req{},
|
||||
"QYGL5A3C": &dto.QYGL5A3CReq{},
|
||||
"QYGL8B4D": &dto.QYGL8B4DReq{},
|
||||
"QYGL9E2F": &dto.QYGL9E2FReq{},
|
||||
"QYGL7C1A": &dto.QYGL7C1AReq{},
|
||||
"QYGL3F8E": &dto.QYGL3F8EReq{},
|
||||
"YYSY4B37": &dto.YYSY4B37Req{},
|
||||
"YYSY4B21": &dto.YYSY4B21Req{},
|
||||
"YYSY6F2E": &dto.YYSY6F2EReq{},
|
||||
"YYSY09CD": &dto.YYSY09CDReq{},
|
||||
"IVYZ0B03": &dto.IVYZ0B03Req{},
|
||||
"IVYZ9363": &dto.IVYZ9363Req{},
|
||||
"IVYZ385E": &dto.IVYZ385EReq{},
|
||||
"IVYZ5733": &dto.IVYZ5733Req{},
|
||||
"FLXG3D56": &dto.FLXG3D56Req{},
|
||||
"FLXG75FE": &dto.FLXG75FEReq{},
|
||||
"FLXG0V3B": &dto.FLXG0V3BReq{},
|
||||
"FLXG0V4B": &dto.FLXG0V4BReq{},
|
||||
"FLXG54F5": &dto.FLXG54F5Req{},
|
||||
"FLXG162A": &dto.FLXG162AReq{},
|
||||
"FLXG0687": &dto.FLXG0687Req{},
|
||||
"FLXGBC21": &dto.FLXGBC21Req{},
|
||||
"FLXG970F": &dto.FLXG970FReq{},
|
||||
"FLXG5876": &dto.FLXG5876Req{},
|
||||
"FLXG9687": &dto.FLXG9687Req{},
|
||||
"FLXGC9D1": &dto.FLXGC9D1Req{},
|
||||
"FLXGCA3D": &dto.FLXGCA3DReq{},
|
||||
"FLXGDEC7": &dto.FLXGDEC7Req{},
|
||||
"JRZQ0A03": &dto.JRZQ0A03Req{},
|
||||
"JRZQ4AA8": &dto.JRZQ4AA8Req{},
|
||||
"JRZQ8203": &dto.JRZQ8203Req{},
|
||||
"JRZQDCBE": &dto.JRZQDCBEReq{},
|
||||
"QYGL2ACD": &dto.QYGL2ACDReq{},
|
||||
"QYGL6F2D": &dto.QYGL6F2DReq{},
|
||||
"QYGL45BD": &dto.QYGL45BDReq{},
|
||||
"QYGL8261": &dto.QYGL8261Req{},
|
||||
"QYGL8271": &dto.QYGL8271Req{},
|
||||
"QYGLB4C0": &dto.QYGLB4C0Req{},
|
||||
"QYGL23T7": &dto.QYGL23T7Req{},
|
||||
"QYGL5A3C": &dto.QYGL5A3CReq{},
|
||||
"QYGL8B4D": &dto.QYGL8B4DReq{},
|
||||
"QYGL9E2F": &dto.QYGL9E2FReq{},
|
||||
"QYGL7C1A": &dto.QYGL7C1AReq{},
|
||||
"QYGL3F8E": &dto.QYGL3F8EReq{},
|
||||
"YYSY4B37": &dto.YYSY4B37Req{},
|
||||
"YYSY4B21": &dto.YYSY4B21Req{},
|
||||
"YYSY6F2E": &dto.YYSY6F2EReq{},
|
||||
"YYSY09CD": &dto.YYSY09CDReq{},
|
||||
"IVYZ0B03": &dto.IVYZ0B03Req{},
|
||||
"YYSYBE08": &dto.YYSYBE08Req{},
|
||||
"YYSYBE08TEST": &dto.YYSYBE08Req{},
|
||||
"YYSYD50F": &dto.YYSYD50FReq{},
|
||||
"YYSYF7DB": &dto.YYSYF7DBReq{},
|
||||
"IVYZ9A2B": &dto.IVYZ9A2BReq{},
|
||||
"IVYZ7F2A": &dto.IVYZ7F2AReq{},
|
||||
"IVYZ4E8B": &dto.IVYZ4E8BReq{},
|
||||
"IVYZ1C9D": &dto.IVYZ1C9DReq{},
|
||||
"IVYZGZ08": &dto.IVYZGZ08Req{},
|
||||
"FLXG8A3F": &dto.FLXG8A3FReq{},
|
||||
"FLXG5B2E": &dto.FLXG5B2EReq{},
|
||||
"COMB298Y": &dto.COMB298YReq{},
|
||||
"COMB86PM": &dto.COMB86PMReq{},
|
||||
"QCXG7A2B": &dto.QCXG7A2BReq{},
|
||||
"COMENT01": &dto.COMENT01Req{},
|
||||
"JRZQ09J8": &dto.JRZQ09J8Req{},
|
||||
"FLXGDEA8": &dto.FLXGDEA8Req{},
|
||||
"FLXGDEA9": &dto.FLXGDEA9Req{},
|
||||
"JRZQ1D09": &dto.JRZQ1D09Req{},
|
||||
"IVYZ2A8B": &dto.IVYZ2A8BReq{},
|
||||
"IVYZ7C9D": &dto.IVYZ7C9DReq{},
|
||||
"IVYZ5E3F": &dto.IVYZ5E3FReq{},
|
||||
"YYSY4F2E": &dto.YYSY4F2EReq{},
|
||||
"YYSY8B1C": &dto.YYSY8B1CReq{},
|
||||
"YYSY6D9A": &dto.YYSY6D9AReq{},
|
||||
"YYSY3E7F": &dto.YYSY3E7FReq{},
|
||||
"FLXG5A3B": &dto.FLXG5A3BReq{},
|
||||
"FLXG9C1D": &dto.FLXG9C1DReq{},
|
||||
"FLXG2E8F": &dto.FLXG2E8FReq{},
|
||||
"JRZQ3C7B": &dto.JRZQ3C7BReq{},
|
||||
"JRZQ8A2D": &dto.JRZQ8A2DReq{},
|
||||
"JRZQ5E9F": &dto.JRZQ5E9FReq{},
|
||||
"JRZQ4B6C": &dto.JRZQ4B6CReq{},
|
||||
"JRZQ7F1A": &dto.JRZQ7F1AReq{},
|
||||
"DWBG6A2C": &dto.DWBG6A2CReq{},
|
||||
"DWBG8B4D": &dto.DWBG8B4DReq{},
|
||||
"FLXG8B4D": &dto.FLXG8B4DReq{},
|
||||
"IVYZ81NC": &dto.IVYZ81NCReq{},
|
||||
"IVYZ2MN6": &dto.IVYZ2MN6Req{},
|
||||
"IVYZ7F3A": &dto.IVYZ7F3AReq{},
|
||||
"IVYZ3P9M": &dto.IVYZ3P9MReq{},
|
||||
"IVYZ3A7F": &dto.IVYZ3A7FReq{},
|
||||
"IVYZ9D2E": &dto.IVYZ9D2EReq{},
|
||||
"DWBG7F3A": &dto.DWBG7F3AReq{},
|
||||
"YYSY8F3A": &dto.YYSY8F3AReq{},
|
||||
"QCXG9P1C": &dto.QCXG9P1CReq{},
|
||||
"JRZQ9E2A": &dto.JRZQ9E2AReq{},
|
||||
"YYSY9A1B": &dto.YYSY9A1BReq{},
|
||||
"YYSY8C2D": &dto.YYSY8C2DReq{},
|
||||
"YYSY7D3E": &dto.YYSY7D3EReq{},
|
||||
"YYSY9E4A": &dto.YYSY9E4AReq{},
|
||||
"JRZQ6F2A": &dto.JRZQ6F2AReq{},
|
||||
"JRZQ8B3C": &dto.JRZQ8B3CReq{},
|
||||
"JRZQ9D4E": &dto.JRZQ9D4EReq{},
|
||||
"FLXG7E8F": &dto.FLXG7E8FReq{},
|
||||
"QYGL5F6A": &dto.QYGL5F6AReq{},
|
||||
"IVYZ6G7H": &dto.IVYZ6G7HReq{},
|
||||
"IVYZ8I9J": &dto.IVYZ8I9JReq{},
|
||||
"JRZQ0L85": &dto.JRZQ0L85Req{},
|
||||
"YYSYD50F": &dto.YYSYD50FReq{},
|
||||
"YYSYF7DB": &dto.YYSYF7DBReq{},
|
||||
"IVYZ9A2B": &dto.IVYZ9A2BReq{},
|
||||
"IVYZ7F2A": &dto.IVYZ7F2AReq{},
|
||||
"IVYZ4E8B": &dto.IVYZ4E8BReq{},
|
||||
"IVYZ1C9D": &dto.IVYZ1C9DReq{},
|
||||
"IVYZGZ08": &dto.IVYZGZ08Req{},
|
||||
"FLXG8A3F": &dto.FLXG8A3FReq{},
|
||||
"FLXG5B2E": &dto.FLXG5B2EReq{},
|
||||
"COMB298Y": &dto.COMB298YReq{},
|
||||
"COMB86PM": &dto.COMB86PMReq{},
|
||||
"QCXG7A2B": &dto.QCXG7A2BReq{},
|
||||
"COMENT01": &dto.COMENT01Req{},
|
||||
"JRZQ09J8": &dto.JRZQ09J8Req{},
|
||||
"FLXGDEA8": &dto.FLXGDEA8Req{},
|
||||
"FLXGDEA9": &dto.FLXGDEA9Req{},
|
||||
"JRZQ1D09": &dto.JRZQ1D09Req{},
|
||||
"IVYZ2A8B": &dto.IVYZ2A8BReq{},
|
||||
"IVYZ7C9D": &dto.IVYZ7C9DReq{},
|
||||
"IVYZ5E3F": &dto.IVYZ5E3FReq{},
|
||||
"YYSY4F2E": &dto.YYSY4F2EReq{},
|
||||
"YYSY8B1C": &dto.YYSY8B1CReq{},
|
||||
"YYSY6D9A": &dto.YYSY6D9AReq{},
|
||||
"YYSY3E7F": &dto.YYSY3E7FReq{},
|
||||
"FLXG5A3B": &dto.FLXG5A3BReq{},
|
||||
"FLXG9C1D": &dto.FLXG9C1DReq{},
|
||||
"FLXG2E8F": &dto.FLXG2E8FReq{},
|
||||
"JRZQ3C7B": &dto.JRZQ3C7BReq{},
|
||||
"JRZQ8A2D": &dto.JRZQ8A2DReq{},
|
||||
"JRZQ5E9F": &dto.JRZQ5E9FReq{},
|
||||
"JRZQ4B6C": &dto.JRZQ4B6CReq{},
|
||||
"JRZQ7F1A": &dto.JRZQ7F1AReq{},
|
||||
"DWBG6A2C": &dto.DWBG6A2CReq{},
|
||||
"DWBG8B4D": &dto.DWBG8B4DReq{},
|
||||
"FLXG8B4D": &dto.FLXG8B4DReq{},
|
||||
"IVYZ81NC": &dto.IVYZ81NCReq{},
|
||||
"IVYZ2MN6": &dto.IVYZ2MN6Req{},
|
||||
"IVYZ7F3A": &dto.IVYZ7F3AReq{},
|
||||
"IVYZ3P9M": &dto.IVYZ3P9MReq{},
|
||||
"IVYZ3A7F": &dto.IVYZ3A7FReq{},
|
||||
"IVYZ9D2E": &dto.IVYZ9D2EReq{},
|
||||
"DWBG7F3A": &dto.DWBG7F3AReq{},
|
||||
"YYSY8F3A": &dto.YYSY8F3AReq{},
|
||||
"QCXG9P1C": &dto.QCXG9P1CReq{},
|
||||
"JRZQ9E2A": &dto.JRZQ9E2AReq{},
|
||||
"YYSY9A1B": &dto.YYSY9A1BReq{},
|
||||
"YYSY8C2D": &dto.YYSY8C2DReq{},
|
||||
"YYSY7D3E": &dto.YYSY7D3EReq{},
|
||||
"YYSY9E4A": &dto.YYSY9E4AReq{},
|
||||
"JRZQ6F2A": &dto.JRZQ6F2AReq{},
|
||||
"JRZQ8B3C": &dto.JRZQ8B3CReq{},
|
||||
"JRZQ9D4E": &dto.JRZQ9D4EReq{},
|
||||
"FLXG7E8F": &dto.FLXG7E8FReq{},
|
||||
"QYGL5F6A": &dto.QYGL5F6AReq{},
|
||||
"IVYZ6G7H": &dto.IVYZ6G7HReq{},
|
||||
"IVYZ8I9J": &dto.IVYZ8I9JReq{},
|
||||
"JRZQ0L85": &dto.JRZQ0L85Req{},
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1240,3 +1244,105 @@ func (s *ProductApplicationServiceImpl) mapFieldTypeToDocType(frontendType strin
|
||||
return "string"
|
||||
}
|
||||
}
|
||||
|
||||
// ExportProductDictionary 导出产品字典
|
||||
func (s *ProductApplicationServiceImpl) ExportProductDictionary(ctx context.Context, format string) ([]byte, error) {
|
||||
// 查询所有启用且可见的产品及其分类信息
|
||||
products, err := s.productManagementService.GetAllProductsForDictionary(ctx)
|
||||
if err != nil {
|
||||
s.logger.Error("获取产品字典数据失败", zap.Error(err))
|
||||
return nil, err
|
||||
}
|
||||
|
||||
if len(products) == 0 {
|
||||
return nil, fmt.Errorf("没有找到符合条件的产品数据")
|
||||
}
|
||||
|
||||
// 按分类分组整理数据
|
||||
categoryGroups := make(map[string][]map[string]interface{})
|
||||
categoryOrder := []string{} // 保持分类顺序
|
||||
|
||||
for _, product := range products {
|
||||
// 获取分类名称
|
||||
categoryName := "未分类"
|
||||
if product.Category != nil {
|
||||
categoryName = product.Category.Name
|
||||
// 如果有二级分类,添加到分类名称中
|
||||
if product.SubCategory != nil && product.SubCategory.Name != "" {
|
||||
categoryName = categoryName + " / " + product.SubCategory.Name
|
||||
}
|
||||
}
|
||||
|
||||
// 如果分类不存在,初始化并添加到顺序列表
|
||||
if _, exists := categoryGroups[categoryName]; !exists {
|
||||
categoryGroups[categoryName] = []map[string]interface{}{}
|
||||
categoryOrder = append(categoryOrder, categoryName)
|
||||
}
|
||||
|
||||
// 添加产品到对应分类
|
||||
productInfo := map[string]interface{}{
|
||||
"category": categoryName,
|
||||
"product_code": product.Code,
|
||||
"product_name": product.Name,
|
||||
"description": product.Description,
|
||||
}
|
||||
categoryGroups[categoryName] = append(categoryGroups[categoryName], productInfo)
|
||||
}
|
||||
|
||||
// 准备导出数据
|
||||
headers := []string{"分类", "产品编码", "产品名称", "产品简介"}
|
||||
columnWidths := []float64{25, 15, 20, 40}
|
||||
|
||||
// 构建数据行
|
||||
var data [][]interface{}
|
||||
for _, categoryName := range categoryOrder {
|
||||
productsInCategory := categoryGroups[categoryName]
|
||||
for i, product := range productsInCategory {
|
||||
// 只有每个分类的第一个产品才显示分类名称
|
||||
var categoryNameForRow interface{}
|
||||
if i == 0 {
|
||||
categoryNameForRow = product["category"]
|
||||
} else {
|
||||
categoryNameForRow = ""
|
||||
}
|
||||
|
||||
row := []interface{}{
|
||||
categoryNameForRow,
|
||||
product["product_code"],
|
||||
product["product_name"],
|
||||
product["description"],
|
||||
}
|
||||
data = append(data, row)
|
||||
}
|
||||
}
|
||||
|
||||
// 计算需要合并的行
|
||||
mergedRegions := [][]int{}
|
||||
currentRow := 1 // 从第1行开始(第0行是表头)
|
||||
for _, categoryName := range categoryOrder {
|
||||
productsCount := len(categoryGroups[categoryName])
|
||||
if productsCount > 1 {
|
||||
// 合并相同分类的单元格:从当前行开始,合并productsCount行,第0列
|
||||
// Excel格式:[startRow, startCol, endRow, endCol]
|
||||
mergedRegions = append(mergedRegions, []int{
|
||||
currentRow, // startRow
|
||||
0, // startCol (分类列)
|
||||
currentRow + productsCount - 1, // endRow
|
||||
0, // endCol
|
||||
})
|
||||
}
|
||||
currentRow += productsCount
|
||||
}
|
||||
|
||||
// 创建导出配置
|
||||
config := &export.ExportConfig{
|
||||
SheetName: "产品字典",
|
||||
Headers: headers,
|
||||
Data: data,
|
||||
ColumnWidths: columnWidths,
|
||||
MergedRegions: mergedRegions,
|
||||
}
|
||||
|
||||
// 使用导出管理器生成文件
|
||||
return s.exportManager.Export(ctx, config, format)
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user