# Copyright (C) 2024 Manuel Bustillo

# frozen_string_literal: true

class AffinitiesController < ApplicationController
  before_action :set_group

  def index
    overridden = @group.affinities.each_with_object({}) do |affinity, acc|
      acc[affinity.another_group(@group).id] = affinity.discomfort
    end

    for_each_group do |group_id|
      overridden[group_id] || GroupAffinity::NEUTRAL
    end
  end

  def bulk_update
    affinities = params.expect(affinities: [%i[group_id affinity]]).map(&:to_h).map do |affinity|
      {
        group_a_id: @group.id,
        group_b_id: affinity[:group_id],
        discomfort: GroupAffinity::MAX_DISCOMFORT - affinity[:affinity]
      }
    end

    GroupAffinity.upsert_all(affinities)

    render json: {}, status: :ok
  rescue ActiveRecord::InvalidForeignKey
    render json: { error: 'At least one of the group IDs provided does not exist.' }, status: :bad_request
  rescue ActiveRecord::StatementInvalid
    render json: { error: 'Invalid group ID or discomfort provided.' }, status: :bad_request
  end

  def default
    for_each_group do |group_id|
      Tables::DiscomfortCalculator.cohesion_discomfort(id_a: @group.id, id_b: group_id).to_f
    end
  end

  private

  def for_each_group
    Group.where.not(id: @group.id)
         .pluck(:id)
         .index_with { |group_id| GroupAffinity::MAX_DISCOMFORT - yield(group_id) }
         .then { |affinities| render json: affinities }
  end

  def set_group
    @group = Group.find(params[:group_id])
  end
end