pipeline->run([ 'raw' => $candidate->raw_markdown ?? $candidate->raw_text ?? '', 'options' => $candidate->options ?? [], ]); $questionType = $payload['question_type'] ?? $this->inferQuestionType($candidate); $question = Question::create([ 'question_code' => $this->buildQuestionCode($candidate), 'question_type' => $questionType, 'stem' => $payload['stem'] ?? $candidate->stem ?? $candidate->raw_text ?? '', 'options' => $payload['options'] ?? $candidate->options ?? null, 'answer' => null, 'solution' => null, 'difficulty' => $payload['difficulty'] ?? 1, 'source_file_id' => $candidate->source_file_id, 'source_paper_id' => $candidate->source_paper_id, 'paper_part_id' => $candidate->part_id, 'meta' => [ 'candidate_id' => $candidate->id, ], ]); QuestionMeta::updateOrCreate( ['question_id' => $question->id], [ 'abilities' => [], 'generation_info' => [ 'source' => 'candidate', 'candidate_id' => $candidate->id, ], 'review_status' => 'pending', ] ); $candidate->status = PreQuestionCandidate::STATUS_ACCEPTED; $candidate->save(); return $question; }); } private function inferQuestionType(PreQuestionCandidate $candidate): string { if (!empty($candidate->options)) { return 'choice'; } return 'short'; } private function buildQuestionCode(PreQuestionCandidate $candidate): string { return sprintf('Q-%s-%d', date('Ymd'), $candidate->id); } }