| 
									
										
										
										
											2025-07-28 01:46:39 +08:00
										 |  |  | package comb | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | import ( | 
					
						
							|  |  |  | 	"context" | 
					
						
							|  |  |  | 	"encoding/json" | 
					
						
							|  |  |  | 	"fmt" | 
					
						
							|  |  |  | 	"sort" | 
					
						
							|  |  |  | 	"sync" | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	"tyapi-server/internal/domains/api/services/processors" | 
					
						
							|  |  |  | 	"tyapi-server/internal/domains/product/entities" | 
					
						
							|  |  |  | 	"tyapi-server/internal/domains/product/services" | 
					
						
							|  |  |  | ) | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | // CombService 组合包服务 | 
					
						
							|  |  |  | type CombService struct { | 
					
						
							|  |  |  | 	productManagementService *services.ProductManagementService | 
					
						
							|  |  |  | 	processorRegistry        map[string]processors.ProcessorFunc | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | // NewCombService 创建组合包服务 | 
					
						
							|  |  |  | func NewCombService(productManagementService *services.ProductManagementService) *CombService { | 
					
						
							|  |  |  | 	return &CombService{ | 
					
						
							|  |  |  | 		productManagementService: productManagementService, | 
					
						
							|  |  |  | 		processorRegistry:        make(map[string]processors.ProcessorFunc), | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | // RegisterProcessor 注册处理器 | 
					
						
							|  |  |  | func (cs *CombService) RegisterProcessor(apiCode string, processor processors.ProcessorFunc) { | 
					
						
							|  |  |  | 	cs.processorRegistry[apiCode] = processor | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | // ProcessCombRequest 处理组合包请求 - 实现 CombServiceInterface | 
					
						
							| 
									
										
										
										
											2025-08-02 02:54:21 +08:00
										 |  |  | func (cs *CombService) ProcessCombRequest(ctx context.Context, params []byte, deps *processors.ProcessorDependencies, packageCode string) (*processors.CombinedResult, error) { | 
					
						
							| 
									
										
										
										
											2025-07-28 01:46:39 +08:00
										 |  |  | 	// 1. 根据组合包code获取产品信息 | 
					
						
							|  |  |  | 	packageProduct, err := cs.productManagementService.GetProductByCode(ctx, packageCode) | 
					
						
							|  |  |  | 	if err != nil { | 
					
						
							|  |  |  | 		return nil, fmt.Errorf("获取组合包信息失败: %s", err.Error()) | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	if !packageProduct.IsPackage { | 
					
						
							|  |  |  | 		return nil, fmt.Errorf("产品 %s 不是组合包", packageCode) | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	// 2. 获取组合包的所有子产品 | 
					
						
							|  |  |  | 	packageItems, err := cs.productManagementService.GetPackageItems(ctx, packageProduct.ID) | 
					
						
							|  |  |  | 	if err != nil { | 
					
						
							|  |  |  | 		return nil, fmt.Errorf("获取组合包子产品失败: %s", err.Error()) | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	if len(packageItems) == 0 { | 
					
						
							|  |  |  | 		return nil, fmt.Errorf("组合包 %s 没有配置子产品", packageCode) | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	// 3. 并发调用所有子产品的处理器 | 
					
						
							|  |  |  | 	results := cs.processSubProducts(ctx, params, deps, packageItems) | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	// 4. 组合结果 | 
					
						
							|  |  |  | 	return cs.combineResults(results) | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | // processSubProducts 并发处理子产品 | 
					
						
							|  |  |  | func (cs *CombService) processSubProducts( | 
					
						
							|  |  |  | 	ctx context.Context, | 
					
						
							|  |  |  | 	params []byte, | 
					
						
							|  |  |  | 	deps *processors.ProcessorDependencies, | 
					
						
							|  |  |  | 	packageItems []*entities.ProductPackageItem, | 
					
						
							| 
									
										
										
										
											2025-08-02 02:54:21 +08:00
										 |  |  | ) []*processors.SubProductResult { | 
					
						
							|  |  |  | 	results := make([]*processors.SubProductResult, 0, len(packageItems)) | 
					
						
							| 
									
										
										
										
											2025-07-28 01:46:39 +08:00
										 |  |  | 	var wg sync.WaitGroup | 
					
						
							|  |  |  | 	var mu sync.Mutex | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	// 并发处理每个子产品 | 
					
						
							|  |  |  | 	for _, item := range packageItems { | 
					
						
							|  |  |  | 		wg.Add(1) | 
					
						
							|  |  |  | 		go func(item *entities.ProductPackageItem) { | 
					
						
							|  |  |  | 			defer wg.Done() | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 			result := cs.processSingleSubProduct(ctx, params, deps, item) | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 			mu.Lock() | 
					
						
							|  |  |  | 			results = append(results, result) | 
					
						
							|  |  |  | 			mu.Unlock() | 
					
						
							|  |  |  | 		}(item) | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	wg.Wait() | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	// 按SortOrder排序 | 
					
						
							|  |  |  | 	sort.Slice(results, func(i, j int) bool { | 
					
						
							|  |  |  | 		return results[i].SortOrder < results[j].SortOrder | 
					
						
							|  |  |  | 	}) | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	return results | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | // processSingleSubProduct 处理单个子产品 | 
					
						
							|  |  |  | func (cs *CombService) processSingleSubProduct( | 
					
						
							|  |  |  | 	ctx context.Context, | 
					
						
							|  |  |  | 	params []byte, | 
					
						
							|  |  |  | 	deps *processors.ProcessorDependencies, | 
					
						
							|  |  |  | 	item *entities.ProductPackageItem, | 
					
						
							| 
									
										
										
										
											2025-08-02 02:54:21 +08:00
										 |  |  | ) *processors.SubProductResult { | 
					
						
							|  |  |  | 	result := &processors.SubProductResult{ | 
					
						
							| 
									
										
										
										
											2025-07-28 01:46:39 +08:00
										 |  |  | 		ApiCode:   item.Product.Code, | 
					
						
							|  |  |  | 		SortOrder: item.SortOrder, | 
					
						
							|  |  |  | 		Success:   false, | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	// 查找对应的处理器 | 
					
						
							|  |  |  | 	processor, exists := cs.processorRegistry[item.Product.Code] | 
					
						
							|  |  |  | 	if !exists { | 
					
						
							|  |  |  | 		result.Error = fmt.Sprintf("未找到处理器: %s", item.Product.Code) | 
					
						
							|  |  |  | 		return result | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	// 调用处理器 | 
					
						
							|  |  |  | 	respBytes, err := processor(ctx, params, deps) | 
					
						
							|  |  |  | 	if err != nil { | 
					
						
							|  |  |  | 		result.Error = err.Error() | 
					
						
							|  |  |  | 		return result | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	// 解析响应 | 
					
						
							|  |  |  | 	var responseData interface{} | 
					
						
							|  |  |  | 	if err := json.Unmarshal(respBytes, &responseData); err != nil { | 
					
						
							|  |  |  | 		result.Error = fmt.Sprintf("解析响应失败: %s", err.Error()) | 
					
						
							|  |  |  | 		return result | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	result.Success = true | 
					
						
							|  |  |  | 	result.Data = responseData | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	return result | 
					
						
							|  |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | // combineResults 组合所有子产品的结果 | 
					
						
							| 
									
										
										
										
											2025-08-02 02:54:21 +08:00
										 |  |  | func (cs *CombService) combineResults(results []*processors.SubProductResult) (*processors.CombinedResult, error) { | 
					
						
							| 
									
										
										
										
											2025-07-28 01:46:39 +08:00
										 |  |  | 	// 构建组合结果 | 
					
						
							| 
									
										
										
										
											2025-08-02 02:54:21 +08:00
										 |  |  | 	combinedResult := &processors.CombinedResult{ | 
					
						
							| 
									
										
										
										
											2025-07-28 01:46:39 +08:00
										 |  |  | 		Responses: results, | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2025-08-02 02:54:21 +08:00
										 |  |  | 	return combinedResult, nil | 
					
						
							| 
									
										
										
										
											2025-07-28 01:46:39 +08:00
										 |  |  | } | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 
 |