module Yt::Actions::List

Public Instance Methods

first!() click to toggle source
# File lib/yt/actions/list.rb, line 12
def first!
  first.tap{|item| raise Errors::NoItems, error_message unless item}
end

Private Instance Methods

attributes_for_new_item(data) click to toggle source

@private Can be overwritten by subclasses that initialize instance with a different set of parameters.

# File lib/yt/actions/list.rb, line 73
def attributes_for_new_item(data)
  {data: data, auth: @auth}
end
eager_load_items_from(items) click to toggle source
# File lib/yt/actions/list.rb, line 89
def eager_load_items_from(items)
  items
end
error_message() click to toggle source
# File lib/yt/actions/list.rb, line 106
def error_message
  {}.tap do |message|
    message[:request_curl] = @list_request.as_curl
    message[:response_body] = JSON(@last_response.body)
  end.to_json if @list_request && @last_response
end
extract_items(list) click to toggle source
# File lib/yt/actions/list.rb, line 126
def extract_items(list)
  list.fetch items_key, []
end
fetch_page(params = {}) click to toggle source
# File lib/yt/actions/list.rb, line 93
def fetch_page(params = {})
  @last_response = list_request(params).run
  token = @last_response.body['nextPageToken']
  items = extract_items @last_response.body
  {items: items, token: token}
end
find_next() click to toggle source
# File lib/yt/actions/list.rb, line 47
def find_next
  @items ||= []
  if @items[@last_index].nil? && more_pages?
    more_items = next_page.map{|data| new_item data}.compact
    @items.concat more_items
  end
  @items[(@last_index +=1) -1]
end
items_key() click to toggle source
# File lib/yt/actions/list.rb, line 130
def items_key
  'items'
end
list() click to toggle source
# File lib/yt/actions/list.rb, line 18
def list
  @last_index, @page_token = 0, nil
  Yt::Iterator.new(-> {total_results}) do |items|
    while next_item = find_next
      items << next_item
    end
    @where_params = {}
  end
end
list_params() click to toggle source
# File lib/yt/actions/list.rb, line 113
def list_params
  path = "/youtube/v3/#{list_resources.camelize :lower}"

  {}.tap do |params|
    params[:method] = :get
    params[:host] = 'www.googleapis.com'
    params[:auth] = @auth
    params[:path] = path
    params[:exptected_response] = Net::HTTPOK
    params[:api_key] = Yt.configuration.api_key if Yt.configuration.api_key
  end
end
list_request(params = {}) click to toggle source
# File lib/yt/actions/list.rb, line 100
def list_request(params = {})
  @list_request = Yt::Request.new(params).tap do |request|
    print "#{request.as_curl}\n" if Yt.configuration.developing?
  end
end
list_resources() click to toggle source
# File lib/yt/actions/list.rb, line 134
def list_resources
  self.class.to_s.demodulize
end
more_pages?() click to toggle source
# File lib/yt/actions/list.rb, line 77
def more_pages?
  @last_index.zero? || @page_token.present?
end
new_item(data) click to toggle source

@return [resource_class] a new resource initialized with one

of the items returned by asking YouTube for a list of resources.
Can be overwritten by subclasses that initialize instance with
a different set of parameters.
# File lib/yt/actions/list.rb, line 66
def new_item(data)
  resource_class.new attributes_for_new_item(data)
end
next_page() click to toggle source
# File lib/yt/actions/list.rb, line 81
def next_page
  params = list_params.dup
  params[:params][:page_token] = @page_token if @page_token
  next_page = fetch_page params
  @page_token = next_page[:token]
  eager_load_items_from next_page[:items]
end
resource_class() click to toggle source
# File lib/yt/actions/list.rb, line 56
def resource_class
  resource_name = list_resources.singularize
  require "yt/models/#{resource_name.underscore}"
  "Yt::Models::#{resource_name}".constantize
end
total_results() click to toggle source

Returns the total number of items that YouTube can provide for the given request, either all in one page or in consecutive pages.

This number comes from the 'totalResults' component of the 'pageInfo' which, accordingly to YouTube documentation, *does not always match the actual number of items in the response*.

For instance, when retrieving a list of channels, 'totalResults' might include inactive channels, which are filtered out from the response.

The only way to obtain the real number of returned items is to iterate through all the pages, which can results in many requests. To avoid this, total_results is provided as a good size estimation.

# File lib/yt/actions/list.rb, line 41
def total_results
  response = list_request(list_params).run
  total_results = response.body.fetch('pageInfo', {})['totalResults']
  total_results ||= extract_items(response.body).size
end