info('开始检查任务重置状态...'); // 获取命令选项 $userId = $this->option('user-id'); $taskId = $this->option('task-id'); $resetType = $this->option('reset-type'); $showAll = $this->option('show-all'); $detailed = $this->option('detailed'); // 验证重置类型 if ($resetType && !in_array($resetType, ['daily', 'weekly', 'monthly', 'seasonal', 'none'])) { $this->error('无效的重置类型。有效值: daily, weekly, monthly, seasonal, none'); return 1; } // 构建查询 $query = TaskUserTask::query(); // 应用过滤条件 if ($userId) { $query->where('user_id', $userId); } if ($taskId) { $query->where('task_id', $taskId); } // 获取用户任务 $userTasks = $query->with('task')->get(); if ($userTasks->isEmpty()) { $this->warn('未找到符合条件的用户任务记录'); return 0; } $this->info("找到 {$userTasks->count()} 条用户任务记录"); // 创建表格头 $headers = ['用户ID', '任务ID', '任务名称', '重置类型', '下次重置时间', '状态', '需要重置']; if ($detailed) { $headers = array_merge($headers, ['上次重置时间', '重置次数', '完成时间', '奖励领取时间']); } $rows = []; $needResetCount = 0; $now = Carbon::now(); foreach ($userTasks as $userTask) { // 获取任务 $task = $userTask->task; if (!$task) { continue; } // 获取重置类型 $taskResetType = $task->reset_type ?? 'none'; // 如果指定了重置类型,且不匹配,则跳过 if ($resetType && $resetType !== $taskResetType) { continue; } // 检查是否需要重置 $needReset = $this->checkNeedReset($userTask, $task, $now); // 如果不显示所有任务,且不需要重置,则跳过 if (!$showAll && !$needReset) { continue; } if ($needReset) { $needResetCount++; } // 准备行数据 $row = [ $userTask->user_id, $userTask->task_id, $task->name ?? "未知任务({$userTask->task_id})", $taskResetType, $userTask->next_reset_time ? $userTask->next_reset_time->format('Y-m-d H:i:s') : '未设置', TASK_STATUS::getDescription(TASK_STATUS::from($userTask->status)), $needReset ? '是' : '否' ]; if ($detailed) { $row = array_merge($row, [ $userTask->last_reset_time ? $userTask->last_reset_time->format('Y-m-d H:i:s') : '未重置', $userTask->reset_count ?? 0, $userTask->completed_at ? $userTask->completed_at->format('Y-m-d H:i:s') : '未完成', $userTask->rewarded_at ? $userTask->rewarded_at->format('Y-m-d H:i:s') : '未领取' ]); } $rows[] = $row; } // 显示表格 $this->table($headers, $rows); // 显示统计信息 $this->info("需要重置的任务数量: {$needResetCount}"); // 显示当前时间 $this->info("当前系统时间: {$now->format('Y-m-d H:i:s')}"); return 0; } /** * 检查任务是否需要重置 * * @param TaskUserTask $userTask 用户任务 * @param Task $task 任务 * @param Carbon $now 当前时间 * @return bool */ protected function checkNeedReset(TaskUserTask $userTask, Task $task, Carbon $now): bool { // 如果任务不需要重置,则返回false if (!$task->reset_type || $task->reset_type === 'none') { return false; } // 如果任务状态不是已完成或已领取奖励,则不需要重置 if (!in_array($userTask->status, [TASK_STATUS::COMPLETED->value, TASK_STATUS::REWARDED->value])) { return false; } // 如果下次重置时间未设置,则计算下次重置时间 if (!$userTask->next_reset_time) { // 如果上次重置时间未设置,则使用当前时间 $lastResetTime = $userTask->last_reset_time ?? $now; // 计算下次重置时间 $nextResetTime = $this->calculateNextResetTime($task->reset_type, $lastResetTime); // 如果下次重置时间已过,则需要重置 return $now->greaterThanOrEqualTo($nextResetTime); } // 如果当前时间已超过下次重置时间,则需要重置 return $now->greaterThanOrEqualTo($userTask->next_reset_time); } /** * 计算下次重置时间 * * @param string $resetType 重置类型 * @param Carbon $lastResetTime 上次重置时间 * @return Carbon */ protected function calculateNextResetTime(string $resetType, Carbon $lastResetTime): Carbon { $resetType = RESET_TYPE::tryFrom($resetType) ?? RESET_TYPE::NONE; // 获取重置间隔(秒) $interval = RESET_TYPE::getInterval($resetType); if ($interval === null) { // 如果没有重置间隔,则返回一个很远的未来时间 return Carbon::now()->addYears(100); } // 计算下次重置时间 return $lastResetTime->copy()->addSeconds($interval); } }