From 968d996a9b0aadf64288e110ba5a2dd5fe31d2bf Mon Sep 17 00:00:00 2001 From: huang <1724659546@qq.com> Date: Thu, 27 Nov 2025 21:47:07 +0800 Subject: [PATCH] =?UTF-8?q?=E4=BF=AEbug?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- internal/domain/recipe/recipe_service.go | 2 +- .../repository/raw_material_repository.go | 19 +++++++++++++------ 2 files changed, 14 insertions(+), 7 deletions(-) diff --git a/internal/domain/recipe/recipe_service.go b/internal/domain/recipe/recipe_service.go index 86e82a5..c7e6871 100644 --- a/internal/domain/recipe/recipe_service.go +++ b/internal/domain/recipe/recipe_service.go @@ -204,7 +204,7 @@ func (r *recipeServiceImpl) GenerateRecipeWithPrioritizedStockRawMaterials(ctx c } referencePrice := recipe.CalculateReferencePricePerKilogram() / 100 - recipe.Description = fmt.Sprintf("使用有库存的 %v 种原料和 %v 种无库存原料计算的库存原料优先使用的配方。 计算时预估成本: %.2f元/kg。", len(stockMaterials), len(noStockMaterials), referencePrice) + recipe.Description = fmt.Sprintf("使用 %v 种有库存原料和 %v 种无库存原料计算的库存原料优先使用的配方。 计算时预估成本: %.2f元/kg。", len(stockMaterials), len(noStockMaterials), referencePrice) // 如果 totalPercentage 小于 100%,说明填充料被使用,这是符合预期的。 // 此时需要在描述中说明需要添加的廉价填充料的百分比。 diff --git a/internal/infra/repository/raw_material_repository.go b/internal/infra/repository/raw_material_repository.go index 78d6d71..96da7b0 100644 --- a/internal/infra/repository/raw_material_repository.go +++ b/internal/infra/repository/raw_material_repository.go @@ -18,7 +18,7 @@ type RawMaterialListOptions struct { NutrientName *string MinReferencePrice *float32 // 参考价格最小值 MaxReferencePrice *float32 // 参考价格最大值 - HasStock *bool // 是否只查询有库存的原料 + HasStock *bool OrderBy string } @@ -123,17 +123,24 @@ func (r *gormRawMaterialRepository) ListRawMaterials(ctx context.Context, opts R db = db.Where("reference_price <= ?", *opts.MaxReferencePrice) } - // 筛选有库存的原料 - if opts.HasStock != nil && *opts.HasStock { + // 筛选有/无库存的原料 + if opts.HasStock != nil { // 内部子查询:生成带有 rn 的结果集,GORM 会自动为 models.RawMaterialStockLog 添加 deleted_at IS NULL rankedLogsQuery := r.db.Model(&models.RawMaterialStockLog{}). Select("raw_material_id, after_quantity, ROW_NUMBER() OVER(PARTITION BY raw_material_id ORDER BY happened_at DESC, id DESC) as rn") - // 外部子查询:从 ranked_logs 中筛选 rn=1 且 after_quantity > 0 的 raw_material_id - // GORM 会将 rankedLogsQuery 作为一个子查询嵌入到 FROM 子句中 + // 外部子查询:从 ranked_logs 中筛选 rn=1 的 raw_material_id latestStockLogSubQuery := r.db.Table("(?) as ranked_logs", rankedLogsQuery). Select("raw_material_id"). - Where("rn = 1 AND after_quantity > 0") + Where("rn = 1") + + if *opts.HasStock { + // 筛选有库存的原料 (after_quantity > 0) + latestStockLogSubQuery = latestStockLogSubQuery.Where("after_quantity > 0") + } else { + // 筛选没有库存的原料 (after_quantity = 0) + latestStockLogSubQuery = latestStockLogSubQuery.Where("after_quantity = 0") + } // 将这个子查询直接应用到主查询的 WHERE id IN (?) 条件中 db = db.Where("id IN (?)", latestStockLogSubQuery)