Class: OpenFec::Response

Inherits:
Object
  • Object
show all
Includes:
Enumerable
Defined in:
lib/open_fec/response.rb

Overview

Wraps FEC API JSON responses with pagination metadata and Enumerable access.

The FEC API uses two pagination models:

  • Offset-based (most endpoints): uses page/pages counters

  • Seek/cursor-based (itemized transactions): uses last_indexes cursors

This class auto-detects which model is in use and exposes a unified #next_page_params method for both.

Examples:

Iterating results

response = OpenFec.candidates.search(name: 'Pelosi')
response.each { |candidate| puts candidate['name'] }

Checking pagination

response.next_page?       # => true
response.next_page_params # => { page: 2 } or { last_index: '456', ... }

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(body, status) ⇒ Response

Returns a new instance of Response.

Parameters:

  • body (Hash, Array)

    parsed JSON response body

  • status (Integer)

    HTTP status code



30
31
32
33
# File 'lib/open_fec/response.rb', line 30

def initialize(body, status)
  @raw    = body
  @status = status
end

Instance Attribute Details

#rawHash, Array (readonly)

Returns raw parsed JSON body.

Returns:

  • (Hash, Array)

    raw parsed JSON body



24
25
26
# File 'lib/open_fec/response.rb', line 24

def raw
  @raw
end

#statusInteger (readonly)

Returns HTTP status code.

Returns:

  • (Integer)

    HTTP status code



26
27
28
# File 'lib/open_fec/response.rb', line 26

def status
  @status
end

Instance Method Details

#[](key) ⇒ Object?

Access a top-level key from the raw response.

Parameters:

  • key (String)

Returns:

  • (Object, nil)


144
145
146
147
148
# File 'lib/open_fec/response.rb', line 144

def [](key)
  return nil unless raw.is_a?(Hash)

  raw[key]
end

#current_pageInteger?

Returns current page number (offset-based only).

Returns:

  • (Integer, nil)

    current page number (offset-based only)



81
82
83
# File 'lib/open_fec/response.rb', line 81

def current_page
  pagination['page']
end

#dig(*keys) ⇒ Object?

Dig into nested keys in the raw response.

Parameters:

  • keys (Array<String>)

Returns:

  • (Object, nil)


153
154
155
156
157
# File 'lib/open_fec/response.rb', line 153

def dig(*keys)
  return nil unless raw.is_a?(Hash)

  raw.dig(*keys)
end

#each {|Hash| ... } ⇒ Object

Yields each result record.

Yields:

  • (Hash)

    individual result record



37
38
39
# File 'lib/open_fec/response.rb', line 37

def each(&)
  results.each(&)
end

#empty?Boolean

Returns true if no results in this page.

Returns:

  • (Boolean)

    true if no results in this page



57
58
59
# File 'lib/open_fec/response.rb', line 57

def empty?
  results.empty?
end

#inspectObject



174
175
176
# File 'lib/open_fec/response.rb', line 174

def inspect
  "#<#{self.class} status=#{status} size=#{size} total_count=#{total_count.inspect} next_page?=#{next_page?}>"
end

#last_indexesHash

Returns cursor keys for seek-based pagination.

Returns:

  • (Hash)

    cursor keys for seek-based pagination



120
121
122
# File 'lib/open_fec/response.rb', line 120

def last_indexes
  pagination['last_indexes'] || {}
end

#next_page?Boolean

Whether there are more pages of results to fetch. Works for both offset-based and seek-based pagination.

Returns:

  • (Boolean)


94
95
96
97
98
99
100
101
102
# File 'lib/open_fec/response.rb', line 94

def next_page?
  return seek_next_page? if seek_paginated?

  page = current_page
  pages = total_pages
  return false if page.nil? || pages.nil?

  page < pages
end

#next_page_numberInteger?

Returns the next page number (offset-based only).

Returns:

  • (Integer, nil)

    the next page number (offset-based only)



105
106
107
108
109
# File 'lib/open_fec/response.rb', line 105

def next_page_number
  return nil unless next_page? && !seek_paginated?

  current_page + 1
end

#next_page_paramsHash?

Returns the query params to fetch the next page of results. For offset-based: ‘{ page: N }`. For seek-based: `{ last_index: “…”, last_<sort_field>: “…” }`.

Returns:

  • (Hash, nil)

    params for next page, or nil if no more pages



129
130
131
132
133
134
135
136
137
# File 'lib/open_fec/response.rb', line 129

def next_page_params
  return nil unless next_page?

  if seek_paginated?
    last_indexes.transform_keys(&:to_sym)
  else
    { page: next_page_number }
  end
end

#paginationHash

Returns raw pagination metadata from the API.

Returns:

  • (Hash)

    raw pagination metadata from the API



64
65
66
67
68
# File 'lib/open_fec/response.rb', line 64

def pagination
  return {} unless raw.is_a?(Hash)

  raw['pagination'] || {}
end

#per_pageInteger?

Returns results per page.

Returns:

  • (Integer, nil)

    results per page



86
87
88
# File 'lib/open_fec/response.rb', line 86

def per_page
  pagination['per_page']
end

#resultsArray<Hash>

Returns the results array from the response.

Returns:

  • (Array<Hash>)


43
44
45
46
47
48
# File 'lib/open_fec/response.rb', line 43

def results
  return raw if raw.is_a?(Array)
  return [] unless raw.is_a?(Hash)

  raw['results'] || []
end

#seek_paginated?Boolean

Whether this response uses seek/cursor-based pagination. True for itemized transaction endpoints (Schedule A, Schedule B).

Returns:

  • (Boolean)


115
116
117
# File 'lib/open_fec/response.rb', line 115

def seek_paginated?
  pagination.key?('last_indexes')
end

#sizeInteger Also known as: length

Returns number of results in this page.

Returns:

  • (Integer)

    number of results in this page



51
52
53
# File 'lib/open_fec/response.rb', line 51

def size
  results.size
end

#success?Boolean

Returns true if HTTP status is 2xx.

Returns:

  • (Boolean)

    true if HTTP status is 2xx



170
171
172
# File 'lib/open_fec/response.rb', line 170

def success?
  status >= 200 && status < 300
end

#to_hHash

Returns:

  • (Hash)


160
161
162
# File 'lib/open_fec/response.rb', line 160

def to_h
  raw.is_a?(Hash) ? raw : { 'results' => raw }
end

#to_jsonString

Returns JSON representation.

Returns:

  • (String)

    JSON representation



165
166
167
# File 'lib/open_fec/response.rb', line 165

def to_json(*)
  to_h.to_json
end

#total_countInteger?

Returns total number of matching records across all pages.

Returns:

  • (Integer, nil)

    total number of matching records across all pages



71
72
73
# File 'lib/open_fec/response.rb', line 71

def total_count
  pagination['count']
end

#total_pagesInteger?

Returns total number of pages (offset-based only).

Returns:

  • (Integer, nil)

    total number of pages (offset-based only)



76
77
78
# File 'lib/open_fec/response.rb', line 76

def total_pages
  pagination['pages']
end