Explorar o código

修正命令逻辑:修复has_crop为0但状态非空闲的问题

- 修正查询逻辑:只查找has_crop=0且status!=0的土地
- 修复操作:将这些土地状态设置为空闲
- 简化代码逻辑,专注于解决特定问题
- 验证修复后数据一致性正常
AI Assistant hai 6 meses
pai
achega
e319541039
Modificáronse 1 ficheiros con 43 adicións e 70 borrados
  1. 43 70
      app/Module/Farm/Commands/FixRemovedCropLandStatusCommand.php

+ 43 - 70
app/Module/Farm/Commands/FixRemovedCropLandStatusCommand.php

@@ -11,7 +11,7 @@ use Illuminate\Support\Facades\Log;
 /**
  * 修复已铲除作物的土地状态命令
  *
- * 修复作物已经铲除(软删除)但土地状态不是空闲的问题
+ * 修复没有作物(has_crop为0)但土地状态不是空闲的问题
  * php artisan farm:fix-removed-crop-land-status --dry-run
  */
 class FixRemovedCropLandStatusCommand extends Command
@@ -31,7 +31,7 @@ class FixRemovedCropLandStatusCommand extends Command
      *
      * @var string
      */
-    protected $description = '修复作物已经铲除(软删除)但土地状态不是空闲的问题';
+    protected $description = '修复没有作物(has_crop为0)但土地状态不是空闲的问题';
 
     /**
      * 执行命令
@@ -44,7 +44,7 @@ class FixRemovedCropLandStatusCommand extends Command
         $userId = $this->option('user');
         $limit = (int) $this->option('limit');
 
-        $this->info('开始检查已铲除作物的土地状态...');
+        $this->info('开始检查没有作物但土地状态不是空闲的问题...');
 
         if ($dryRun) {
             $this->warn('运行在模拟模式,不会实际修改数据');
@@ -85,7 +85,7 @@ class FixRemovedCropLandStatusCommand extends Command
 
     /**
      * 获取有问题的土地数据
-     * 查找作物已软删除但土地状态不是空闲的情况
+     * 查找没有作物(has_crop为0)但土地状态不是空闲的情况
      *
      * @param string|null $userId
      * @param int $limit
@@ -93,64 +93,43 @@ class FixRemovedCropLandStatusCommand extends Command
      */
     private function getProblematicLands(?string $userId, int $limit): \Illuminate\Support\Collection
     {
-        // 先获取有软删除作物的土地ID列表
-        $landsWithDeletedCrops = DB::table('farm_land_users')
-            ->join('farm_crops', 'farm_land_users.id', '=', 'farm_crops.land_id')
-            ->select('farm_land_users.id')
-            ->whereNotNull('farm_crops.deleted_at')
-            ->where('farm_land_users.status', '!=', LAND_STATUS::IDLE->value)
+        // 查找has_crop为0但状态不是空闲的土地
+        $query = DB::table('farm_land_users')
+            ->select([
+                'id as land_id',
+                'user_id',
+                'status as land_status',
+                'has_crop'
+            ])
+            ->where('has_crop', 0) // has_crop为0(没有作物)
+            ->where('status', '!=', LAND_STATUS::IDLE->value) // 状态不是空闲
             ->when($userId, function ($query, $userId) {
-                return $query->where('farm_land_users.user_id', $userId);
+                return $query->where('user_id', $userId);
             })
-            ->distinct()
-            ->pluck('farm_land_users.id');
-
-        // 获取没有未删除作物的土地ID列表
-        $landsWithoutActiveCrops = DB::table('farm_land_users')
-            ->leftJoin('farm_crops', function ($join) {
-                $join->on('farm_land_users.id', '=', 'farm_crops.land_id')
-                     ->whereNull('farm_crops.deleted_at');
-            })
-            ->select('farm_land_users.id')
-            ->whereNull('farm_crops.id')
-            ->where('farm_land_users.status', '!=', LAND_STATUS::IDLE->value)
-            ->when($userId, function ($query, $userId) {
-                return $query->where('farm_land_users.user_id', $userId);
-            })
-            ->pluck('farm_land_users.id');
+            ->limit($limit);
 
-        // 合并所有有问题的土地ID
-        $allProblematicLandIds = $landsWithDeletedCrops->concat($landsWithoutActiveCrops)->unique()->take($limit);
+        $results = $query->get();
 
-        // 获取详细信息
-        $results = collect();
-        foreach ($allProblematicLandIds as $landId) {
-            $land = DB::table('farm_land_users')->where('id', $landId)->first();
-            if (!$land) continue;
+        // 添加问题类型标识和额外信息
+        return $results->map(function ($item) {
+            // 检查是否有未删除的作物(用于验证has_crop字段的正确性)
+            $activeCrops = DB::table('farm_crops')
+                ->where('land_id', $item->land_id)
+                ->whereNull('deleted_at')
+                ->count();
 
-            // 获取该土地的软删除作物信息
+            // 检查是否有软删除的作物
             $deletedCrops = DB::table('farm_crops')
-                ->where('land_id', $landId)
+                ->where('land_id', $item->land_id)
                 ->whereNotNull('deleted_at')
-                ->get();
-
-            $item = (object) [
-                'land_id' => $land->id,
-                'user_id' => $land->user_id,
-                'land_status' => $land->status,
-                'has_crop' => $land->has_crop,
-                'deleted_crops_count' => $deletedCrops->count(),
-                'crop_ids' => $deletedCrops->pluck('id')->implode(','),
-                'first_deleted_at' => $deletedCrops->min('deleted_at'),
-                'last_deleted_at' => $deletedCrops->max('deleted_at'),
-                'seed_ids' => $deletedCrops->pluck('seed_id')->unique()->implode(',')
-            ];
+                ->count();
 
+            $item->active_crops_count = $activeCrops;
+            $item->deleted_crops_count = $deletedCrops;
             $item->problem_type = $this->getProblemType($item);
-            $results->push($item);
-        }
 
-        return $results;
+            return $item;
+        });
     }
 
     /**
@@ -161,13 +140,11 @@ class FixRemovedCropLandStatusCommand extends Command
      */
     private function getProblemType(object $item): string
     {
-        if ($item->deleted_crops_count > 0) {
-            return '作物已软删除但土地非空闲';
-        } elseif ($item->deleted_crops_count == 0) {
-            return '土地无作物但状态非空闲';
+        if ($item->active_crops_count > 0) {
+            return 'has_crop为0但实际有活跃作物';
+        } else {
+            return 'has_crop为0且状态非空闲';
         }
-
-        return '其他问题';
     }
 
     /**
@@ -184,7 +161,7 @@ class FixRemovedCropLandStatusCommand extends Command
         foreach ($groupedData as $problemType => $problemItems) {
             $this->info("\n=== {$problemType} ({$problemItems->count()} 条) ===");
 
-            $headers = ['土地ID', '用户ID', '当前土地状态', 'has_crop', '软删除作物数', '作物IDs', '最后删除时间', '种子IDs'];
+            $headers = ['土地ID', '用户ID', '当前土地状态', 'has_crop', '活跃作物数', '软删除作物数'];
             $rows = [];
 
             foreach ($problemItems as $item) {
@@ -193,10 +170,8 @@ class FixRemovedCropLandStatusCommand extends Command
                     $item->user_id,
                     $this->getLandStatusName($item->land_status),
                     $item->has_crop ? '是' : '否',
-                    $item->deleted_crops_count,
-                    $item->crop_ids ? (strlen($item->crop_ids) > 50 ? substr($item->crop_ids, 0, 47) . '...' : $item->crop_ids) : 'N/A',
-                    $item->last_deleted_at ?? 'N/A',
-                    $item->seed_ids ?? 'N/A'
+                    $item->active_crops_count,
+                    $item->deleted_crops_count
                 ];
             }
 
@@ -257,23 +232,21 @@ class FixRemovedCropLandStatusCommand extends Command
         $oldStatus = $land->status;
         $oldHasCrop = $land->has_crop;
 
-        // 设置土地状态为空闲
+        // 如果has_crop为0但状态不是空闲,将状态设置为空闲
         $land->status = LAND_STATUS::IDLE->value;
-        $land->updateHasCrop(); // 这会将has_crop设置为false
+        $land->updateHasCrop(); // 这会根据状态更新has_crop字段
         $land->save();
 
-        Log::info('已铲除作物土地状态修复', [
+        Log::info('修复has_crop为0但状态非空闲的土地', [
             'land_id' => $land->id,
             'user_id' => $land->user_id,
+            'active_crops_count' => $item->active_crops_count,
             'deleted_crops_count' => $item->deleted_crops_count,
-            'crop_ids' => $item->crop_ids,
             'old_status' => $oldStatus,
             'new_status' => $land->status,
             'old_has_crop' => $oldHasCrop,
             'new_has_crop' => $land->has_crop,
-            'problem_type' => $item->problem_type,
-            'first_deleted_at' => $item->first_deleted_at,
-            'last_deleted_at' => $item->last_deleted_at
+            'problem_type' => $item->problem_type
         ]);
     }