class GekanatorGamesController < ApplicationController def create return head :not_found unless current_user&.admin? guessed_post_id = params.require(:guessed_post_id) correct_post_id = params[:correct_post_id].presence answers = params.require(:answers).as_json game = GekanatorGame.new( user: current_user, guessed_post_id:, correct_post_id:, won: correct_post_id.present? && guessed_post_id.to_i == correct_post_id.to_i, question_count: answers.length, answers:) if game.save render json: { id: game.id }, status: :created else render json: { errors: game.errors.full_messages }, status: :unprocessable_entity end end def extra_questions return head :not_found unless current_user&.admin? game = GekanatorGame.find_by(id: params[:id]) return head :not_found unless game asked_ids = Array(game.answers).filter_map { |answer| answer['questionId'] || answer[:questionId] } existing_example_ids = GekanatorQuestionExample.where(post_id: game.correct_post_id) .select(:gekanator_question_id) questions = GekanatorQuestion .accepted .where(kind: 'post_similarity', source: 'user_suggested') .where.not(id: existing_example_ids) .order(priority_weight: :desc, id: :asc) render json: { questions: questions.filter_map { |question| json = extra_question_json(question) next if asked_ids.include?(json[:id].to_s) next if asked_ids.include?("post-similarity:#{ json[:id] }") json }.first(2) } end def extra_question_answers return head :not_found unless current_user&.admin? game = GekanatorGame.find_by(id: params[:id]) return head :not_found unless game answer_params = params.require(:answers) if !answer_params.is_a?(Array) return render_validation_error fields: { answers: ['配列で指定してください.'] } end answers = answer_params.map { |answer| { question_id: answer.require(:question_id), answer: answer.require(:answer) } } questions = GekanatorQuestion.where(id: answers.map { _1[:question_id] }) question_by_id = questions.index_by(&:id) if questions.length != answers.length return render_validation_error fields: { answers: ['質問が見つかりません.'] } end if questions.any? { |question| question.status != 'accepted' || question.kind != 'post_similarity' } return render_validation_error fields: { answers: ['質問が不正です.'] } end ActiveRecord::Base.transaction do answers.each do |item| question = question_by_id[item[:question_id]] example = GekanatorQuestionExample.find_or_initialize_by( gekanator_question: question, post: game.correct_post, user: current_user) example.assign_attributes( gekanator_game: game, answer: item[:answer], source: 'post_game_extra', weight: 1.0) example.save! end end render json: { count: answers.length }, status: :created end private def extra_question_json question { id: question.id, text: question.text, source: question.source, priority_weight: question.priority_weight } end end