module Bits
  class User < Bits::Base
    self.primary_attribute = :id

    attributes :id, :balance, :banned, :ban_annotation, :opted_out, :opt_out_annotation, :min_bits, :min_bits_emote, :pin_top_cheers, :recent_cheer_min, :recent_cheer_timeout_ms, :cheermote_download_url, :badge_tiers

    def self.find(id)
      balance_response = bits_balance(id)
      return from_errors('Failed to load balance') unless balance_response.success?

      bits_channel_settings_response = get "/authed/admin/channels/#{id}"
      return from_errors('Failed to load channel info') unless bits_channel_settings_response.success?

      banned = false
      ban_annotation = ''
      bits_user_banned_response = get "/authed/admin/users/#{id}/banned"
      if bits_user_banned_response.status != 404
        return from_errors('Failed to load bits user banned status') unless bits_user_banned_response.success?
        banned = bits_user_banned_response.body['banned']
        ban_annotation = bits_user_banned_response.body['annotation']
      end

      opted_out = false
      opt_out_annotation = ''
      bits_channel_opted_out_response = get "/authed/admin/channels/#{id}/opt-out"
      if bits_channel_opted_out_response.status != 404
        return from_errors('Failed to load bits channel opt-out status') unless bits_channel_opted_out_response.success?
        opted_out = bits_channel_opted_out_response.body['optedOut']
        opt_out_annotation = bits_channel_opted_out_response.body['annotation']
      end

      bits_badge_tiers_response = get "/authed/admin/badges/#{id}/tiers"
      return from_errors('Failed to load bits badge tiers') unless bits_badge_tiers_response.success?

      cheermote_download_url = "/bits/users/#{id}/download_cheermotes"
      return from_attributes(
        :id => id,
        :balance => balance_response.body['balance'],
        :banned => banned,
        :ban_annotation => ban_annotation,
        :opted_out => opted_out,
        :opt_out_annotation => opt_out_annotation,
        :min_bits => bits_channel_settings_response.body['min_bits'],
        :min_bits_emote => bits_channel_settings_response.body['min_bits_emote'],
        :pin_top_cheers => bits_channel_settings_response.body['pin_top_cheers'],
        :recent_cheer_min => bits_channel_settings_response.body['recent_cheer_min'],
        :recent_cheer_timeout_ms => bits_channel_settings_response.body['recent_cheer_timeout_ms'],
        :cheermote_download_url => cheermote_download_url,
        :badge_tiers => bits_badge_tiers_response.body['tiers'].sort_by {|t| t['threshold']},
      )
    end

    def self.bits_balance(user_id)
      get "/authed/admin/balance/#{user_id}"
    end

    def set_ban_status(target_ban_status, reason, current_user_ldap)
      body = JSON.dump({
        banned: target_ban_status,
        bannedBy: current_user_ldap,
        annotation: reason,
       })

      put(
        "/authed/admin/users/#{id}/banned",
        body: body
      )
    end

    def get_transactions(cursor)
      get "/authed/admin/users/#{id}/events", params: { :cursor => cursor }
    end

    def set_opt_out_status(target_opt_out_status, reason)
      body = JSON.dump({
        optedOut: target_opt_out_status,
        annotation: reason,
       })

      put(
        "/authed/admin/channels/#{id}/opt-out",
        body: body
      )
    end

    def add_bits(bits_amount, reason, current_user_ldap, notify_user, origin)
      body = JSON.dump({
        AmountOfBitsToAdd: bits_amount,
        TypeOfBitsToAdd: 'CB_0',
        EventId: SecureRandom.uuid,
        TwitchUserId: id.to_s,
        AdminUserId: current_user_ldap,
        AdminReason: reason,
        NotifyUser: self.class.booleanize(notify_user),
        Origin: origin
      })

      post(
        "/authed/admin/addBits",
        body: body
      )
    end

    def add_bits_for_campaign(campaign_id, current_user_ldap)
      body = JSON.dump({
        BulkGrantCampaignID: campaign_id,
        EventId: SecureRandom.uuid,
        TwitchUserId: id.to_s,
        AdminUserId: current_user_ldap,
      })

      post(
        "/authed/admin/addBits",
        body: body
      )
    end

    def remove_bits(bits_amount, reason, current_user_ldap)
      body = JSON.dump({
        AmountOfBitsToRemove: bits_amount,
        TypeOfBitsToAdd: 'CB_0',
        EventId: SecureRandom.uuid,
        TwitchUserId: id.to_s,
        AdminUserId: current_user_ldap,
        AdminReason: reason,
      })

      post(
        "/authed/admin/removeBits",
        body: body
      )
    end

    def moderate_cheermote
      delete "/authed/admin/channels/#{id}/images"
    end

    def update_badge_tiers(tiers)
      body = JSON.dump({
        tiers: tiers,
      })

      patch(
        "/authed/admin/badges/#{id}/tiers",
        body: body
      )
    end

    def download_cheermotes
      get "/authed/admin/channels/#{id}/images"
    end
  end
end
