class EasyTrialExpirationController < ApplicationController

  before_action :find_owner, except: [:limit_reached]
  before_action :verify_owner, except: [:limit_reached, :deactivate_entities_modal]

  def deactivate_entities
    project_ids = params['active']['project_ids'] if params['active']
    project_ids ||= []
    user_ids = params['active']['user_ids'] if params['active']
    user_ids ||= []

    if EasyLicenseManager.active_project_limit_exceeded?
      projects_to_archive = Project.where.not(id: project_ids).pluck(:lft, :rgt)

      condition = []
      projects_to_archive.each do |lft, rgt|
        condition << "(lft >= #{lft} AND rgt <= #{rgt})"
      end

      condition = condition.join(' OR ')

      Project.non_templates.where(condition).where.not(status: Project::STATUS_ARCHIVED).update_all(status: Project::STATUS_ARCHIVED, updated_on: Time.now)
    end

    if EasyLicenseManager.active_user_limit_exceeded?
      User.active.where.not(id: @owner.id).where.not(id: user_ids).update_all(status: User::STATUS_LOCKED, updated_on: Time.now)
    end

    redirect_to root_path
  end

  def deactivate_entities_modal
    if User.current == @owner
      @form_path = easy_trial_expiration_deactivate_entities_path
      @exceeded_limits = EasyLicenseManager.exceeded_limits
      @partial_name = 'easy_trial_expiration/entity_selection_form'
      @multiple_limits_exceeded = @exceeded_limits.size > 1

      if @exceeded_limits[:active_user_limit_exceeded]
        @users = User.active.sorted.to_a
        @user_limit = EasyLicenseManager.get_internal_user_limit
      end

      if @exceeded_limits[:active_project_limit_exceeded]
        @projects = projects_for_parent
        @project_limit = EasyLicenseManager.get_active_project_limit
      end
    else
      @exceeded_limits = {}
      @partial_name = 'easy_trial_expiration/regular_user'
    end

    respond_to do |format|
      format.js
    end
  end

  def activate_entities
    if params['active'] && params['active']['all_projects']
      projects = Project.archived.status_changeable
      projects.update_all(status: Project::STATUS_ACTIVE, updated_on: Time.now)
    elsif params['active'] && params['active']['project_ids']
      project_ids = params['active']['project_ids']
      project_ids ||= []

      projects_to_activate = Project.where(id: project_ids).pluck(:lft, :rgt)

      condition = []
      projects_to_activate.each do |lft, rgt|
        condition << "(lft <= #{lft} AND rgt >= #{rgt})"
      end

      condition = condition.join(' OR ')

      Project.archived.status_changeable.where(condition).update_all(status: Project::STATUS_ACTIVE, updated_on: Time.now) if condition.present?
    end

    if params['active'] && params['active']['all_users']
      User.where(status: User::STATUS_LOCKED).update_all(status: User::STATUS_ACTIVE, updated_on: Time.now)
    elsif params['active'] && params['active']['user_ids']
      user_ids = params['active']['user_ids']
      user_ids ||= []
      User.where(status: User::STATUS_LOCKED, id: user_ids).update_all(status: User::STATUS_ACTIVE, updated_on: Time.now)
    end

    first_login_after_upgrade = EasySetting.find_by(name: :first_login_after_upgrade)
    if first_login_after_upgrade
      first_login_after_upgrade.value = false
      first_login_after_upgrade.save
    end

    redirect_back_or_default home_url
  end

  def activate_entities_modal
    @form_path = easy_trial_expiration_activate_entities_path
    locked_user_count = User.where(status: User::STATUS_LOCKED).count
    archived_project_count = Project.archived.status_changeable.count

    if locked_user_count > 0
      active_user_count = EasyLicenseManager.get_active_user_count
      active_user_limit = EasyLicenseManager.get_internal_user_limit

      @activate_users = active_user_count < active_user_limit
      @show_activate_all_users_button = (active_user_count + locked_user_count) < active_user_limit
    end

    if archived_project_count > 0
      active_project_count = EasyLicenseManager.get_active_project_count
      active_project_limit = EasyLicenseManager.get_active_project_limit

      @activate_projects = active_project_count < active_project_limit
      @show_activate_all_projects_button = (active_project_count + archived_project_count) < active_project_limit
    end

    if (!@activate_users && !@activate_projects)
      first_login_after_upgrade = EasySetting.find_by(name: :first_login_after_upgrade)

      if first_login_after_upgrade
        first_login_after_upgrade.value = false
        first_login_after_upgrade.save
      end

      return render text: ''
    end

    if @activate_users
      @users = User.where(status: User::STATUS_LOCKED).sorted.to_a
      @user_limit = EasyLicenseManager.get_internal_user_limit - EasyLicenseManager.get_active_user_count
    end

    if @activate_projects
      @projects = projects_for_parent(nil, true)
      @project_limit = EasyLicenseManager.get_active_project_limit - EasyLicenseManager.get_active_project_count
      @show_archived = true
    end

    respond_to do |format|
      format.js
    end
  end

  def projects
    find_parent if params[:root_id]
    archived = params[:archived]
    parent_id = @parent ? @parent.id : nil
    @projects = projects_for_parent(parent_id, archived)

    if request.xhr?
      render partial: 'easy_trial_expiration/projects', locals: { projects: @projects, show_archived: archived }
    end
  end

  def limit_reached
    respond_to do |format|
      format.js
    end
  end

  private
  # returns projects with given parent_id that have at least one child with given status
  def projects_for_parent(parent_id=nil, archived=false)
    @query = EasyProjectQuery.new
    @query.sort_criteria << ["lft", "asc"]
    @query.entity_scope = Project.where("EXISTS ( SELECT 1 FROM projects as children WHERE children.lft >= projects.lft AND children.rgt <= projects.rgt AND children.status #{'!' unless archived}= #{Project::STATUS_ARCHIVED})")
    @query.add_additional_scope Project.status_changeable
    @query.add_additional_statement Project.arel_table[:parent_id].eq(parent_id).to_sql
    @query.entities
  end

  def find_parent
    @parent = Project.find(params[:root_id])
  rescue ActiveRecord::RecordNotFound
  end

  def find_owner
    @owner = User.owner
  end

  def verify_owner
    @owner ||= User.owner
    return render_403 unless User.current == @owner
  end

end
