module Transactions
  class Entry < Transactions::Base

    attributes :twirp

    def self.parse_search_type(params)
      if params[:event_search_type].present?
        case params[:event_search_type]
        when "EXTENSION"
          return SearchTransactionType::EXTENSION
        when "ONSITE"
          return SearchTransactionType::ONSITE
        end
      end
    end

    # Could be a user_id or user_login
    def self.get_user_id(search)
      if /^\d+$/.match?(search)
        return search
      else
        user = Twitch::User.find_by_login(search)

        raise "Could not find Twitch user with login #{search}" if user.nil?

        return user.id.to_s
      end
    end

    def self.get_user_login(user_id)
      if user_id.empty?
        return ""
      end

      user = Twitch::User.find(user_id)

      if user.nil?
        return ""
      end

      user.login
    end

    def self.parse_date_filters(params)
      event_after = Google::Protobuf::Timestamp.new
      if params[:start_event_time].present?
        start_event_datetime = params[:start_event_time].to_datetime
        event_after = Google::Protobuf::Timestamp.new(seconds: start_event_datetime.to_i, nanos: start_event_datetime.nsec)
      end

      event_before = Google::Protobuf::Timestamp.new(seconds: Time.now.to_i)
      if params[:end_event_time].present?
        end_event_datetime = params[:end_event_time].to_datetime
        event_before = Google::Protobuf::Timestamp.new(seconds: end_event_datetime.to_i, nanos: end_event_datetime.nsec)
      end

      {
        :event_after => event_after,
        :event_before => event_before
      }
    end

    def self.search(params)
      if !params[:user].empty? && !params[:channel].empty?
        flash[:error] = "cannot provide both user and channel"
        return
      end

      if params[:user].empty? && params[:channel].empty?
        flash[:error] = "must provide a user or channel"
        return
      end

      search_type = parse_search_type(params)
      date_filters = parse_date_filters(params)

      req = {
        cursor: params[:cursor],
        event_after: date_filters[:event_after],
        event_before: date_filters[:event_before],
        search_type: search_type,
      }

      if !params[:user].empty?
        req[:user_id] = get_user_id(params[:user])
      elsif !params[:channel].empty?
        req[:channel_id] = get_user_id(params[:channel])
      end

      response = client.search_transactions(SearchTransactionsReq.new(req))

      raise response.error.msg if response.error

      transactions = response.data.transactions.map do |twirp_tx|
        tx = twirp_tx.to_h
        tx[:user_login] = get_user_login(tx[:user_id])
        tx[:channel_login] = get_user_login(tx[:channel_id])

        tx
      end

      {
        "transactions" => transactions,
        "cursor" => response.data["cursor"]
      }
    end
  end
end
