searchapi 1.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/README.md +175 -0
- data/bin/test +14 -0
- data/lib/searchapi/error_result.rb +50 -0
- data/lib/searchapi/google_finance_options.rb +40 -0
- data/lib/searchapi/google_finance_request.rb +26 -0
- data/lib/searchapi/google_finance_result.rb +262 -0
- data/lib/searchapi/google_flights_options.rb +85 -0
- data/lib/searchapi/google_flights_request.rb +25 -0
- data/lib/searchapi/google_flights_result.rb +275 -0
- data/lib/searchapi/google_images_options.rb +64 -0
- data/lib/searchapi/google_images_request.rb +26 -0
- data/lib/searchapi/google_images_result.rb +133 -0
- data/lib/searchapi/google_light_options.rb +43 -0
- data/lib/searchapi/google_light_request.rb +26 -0
- data/lib/searchapi/google_light_result.rb +198 -0
- data/lib/searchapi/google_local_options.rb +40 -0
- data/lib/searchapi/google_local_request.rb +26 -0
- data/lib/searchapi/google_local_result.rb +85 -0
- data/lib/searchapi/google_news_light_options.rb +47 -0
- data/lib/searchapi/google_news_light_request.rb +26 -0
- data/lib/searchapi/google_news_light_result.rb +94 -0
- data/lib/searchapi/google_news_options.rb +53 -0
- data/lib/searchapi/google_news_portal_options.rb +40 -0
- data/lib/searchapi/google_news_portal_request.rb +89 -0
- data/lib/searchapi/google_news_portal_result.rb +137 -0
- data/lib/searchapi/google_news_request.rb +26 -0
- data/lib/searchapi/google_news_result.rb +129 -0
- data/lib/searchapi/google_scholar_options.rb +48 -0
- data/lib/searchapi/google_scholar_request.rb +26 -0
- data/lib/searchapi/google_scholar_result.rb +195 -0
- data/lib/searchapi/google_search_options.rb +67 -0
- data/lib/searchapi/google_search_request.rb +26 -0
- data/lib/searchapi/google_search_result.rb +301 -0
- data/lib/searchapi/helpers.rb +10 -0
- data/lib/searchapi/instagram_profile_options.rb +31 -0
- data/lib/searchapi/instagram_profile_request.rb +26 -0
- data/lib/searchapi/instagram_profile_result.rb +117 -0
- data/lib/searchapi/module_methods.rb +80 -0
- data/lib/searchapi/request.rb +25 -0
- data/lib/searchapi/response_methods.rb +14 -0
- data/lib/searchapi/tiktok_profile_options.rb +31 -0
- data/lib/searchapi/tiktok_profile_request.rb +26 -0
- data/lib/searchapi/tiktok_profile_result.rb +71 -0
- data/lib/searchapi/version.rb +3 -0
- data/lib/searchapi/youtube_search_options.rb +62 -0
- data/lib/searchapi/youtube_search_request.rb +26 -0
- data/lib/searchapi/youtube_search_result.rb +411 -0
- data/lib/searchapi.rb +70 -0
- data/searchapi.gemspec +37 -0
- metadata +164 -0
|
@@ -0,0 +1,275 @@
|
|
|
1
|
+
require 'forwardable'
|
|
2
|
+
|
|
3
|
+
module SearchAPI
|
|
4
|
+
|
|
5
|
+
# Google Flights Search metadata
|
|
6
|
+
GoogleFlightsMetadataSchema = DynamicSchema::Struct.define do
|
|
7
|
+
id String
|
|
8
|
+
status String
|
|
9
|
+
created_at String, as: :created_at
|
|
10
|
+
request_time_taken Float, as: :request_time_taken
|
|
11
|
+
parsing_time_taken Float, as: :parsing_time_taken
|
|
12
|
+
total_time_taken Float, as: :total_time_taken
|
|
13
|
+
request_url String, as: :request_url
|
|
14
|
+
html_url String, as: :html_url
|
|
15
|
+
json_url String, as: :json_url
|
|
16
|
+
end
|
|
17
|
+
|
|
18
|
+
class GoogleFlightsMetadata < GoogleFlightsMetadataSchema
|
|
19
|
+
end
|
|
20
|
+
|
|
21
|
+
# Google Flights Search parameters
|
|
22
|
+
GoogleFlightsParametersSchema = DynamicSchema::Struct.define do
|
|
23
|
+
engine String
|
|
24
|
+
departure_id String, as: :departure_id
|
|
25
|
+
arrival_id String, as: :arrival_id
|
|
26
|
+
currency String
|
|
27
|
+
hl String
|
|
28
|
+
gl String
|
|
29
|
+
outbound_date String, as: :outbound_date
|
|
30
|
+
return_date String, as: :return_date
|
|
31
|
+
flight_type String, as: :flight_type
|
|
32
|
+
travel_class String, as: :travel_class
|
|
33
|
+
stops String
|
|
34
|
+
sort_by String, as: :sort_by
|
|
35
|
+
adults Integer
|
|
36
|
+
children Integer
|
|
37
|
+
infants_in_seat Integer, as: :infants_in_seat
|
|
38
|
+
infants_on_lap Integer, as: :infants_on_lap
|
|
39
|
+
end
|
|
40
|
+
|
|
41
|
+
class GoogleFlightsParameters < GoogleFlightsParametersSchema
|
|
42
|
+
end
|
|
43
|
+
|
|
44
|
+
# Airport details
|
|
45
|
+
GoogleFlightsAirportSchema = DynamicSchema::Struct.define do
|
|
46
|
+
name String
|
|
47
|
+
id String
|
|
48
|
+
date String
|
|
49
|
+
time String
|
|
50
|
+
end
|
|
51
|
+
|
|
52
|
+
class GoogleFlightsAirport < GoogleFlightsAirportSchema
|
|
53
|
+
end
|
|
54
|
+
|
|
55
|
+
# Detected extensions (amenities)
|
|
56
|
+
GoogleFlightsExtensionsSchema = DynamicSchema::Struct.define do
|
|
57
|
+
has_power_and_usb_outlets [ TrueClass, FalseClass ], as: :has_power_and_usb_outlets
|
|
58
|
+
has_personal_video_screen [ TrueClass, FalseClass ], as: :has_personal_video_screen
|
|
59
|
+
has_live_tv [ TrueClass, FalseClass ], as: :has_live_tv
|
|
60
|
+
has_on_demand_video [ TrueClass, FalseClass ], as: :has_on_demand_video
|
|
61
|
+
has_stream_video_to_own_device [ TrueClass, FalseClass ], as: :has_stream_video_to_own_device
|
|
62
|
+
wifi String
|
|
63
|
+
seat_type String, as: :seat_type
|
|
64
|
+
legroom_short String, as: :legroom_short
|
|
65
|
+
legroom_long String, as: :legroom_long
|
|
66
|
+
carbon_emission Float, as: :carbon_emission
|
|
67
|
+
end
|
|
68
|
+
|
|
69
|
+
class GoogleFlightsExtensions < GoogleFlightsExtensionsSchema
|
|
70
|
+
end
|
|
71
|
+
|
|
72
|
+
# Flight segment
|
|
73
|
+
GoogleFlightsSegmentSchema = DynamicSchema::Struct.define do
|
|
74
|
+
departure_airport GoogleFlightsAirport, as: :departure_airport
|
|
75
|
+
arrival_airport GoogleFlightsAirport, as: :arrival_airport
|
|
76
|
+
duration Integer
|
|
77
|
+
airplane String
|
|
78
|
+
airline String
|
|
79
|
+
airline_logo String, as: :airline_logo
|
|
80
|
+
travel_class String, as: :travel_class
|
|
81
|
+
flight_number String, as: :flight_number
|
|
82
|
+
ticket_also_sold_by String, array: true, as: :ticket_also_sold_by
|
|
83
|
+
is_overnight [ TrueClass, FalseClass ], as: :is_overnight
|
|
84
|
+
is_often_delayed [ TrueClass, FalseClass ], as: :is_often_delayed
|
|
85
|
+
extensions String, array: true
|
|
86
|
+
detected_extensions GoogleFlightsExtensions, as: :detected_extensions
|
|
87
|
+
end
|
|
88
|
+
|
|
89
|
+
class GoogleFlightsSegment < GoogleFlightsSegmentSchema
|
|
90
|
+
end
|
|
91
|
+
|
|
92
|
+
# Layover
|
|
93
|
+
GoogleFlightsLayoverSchema = DynamicSchema::Struct.define do
|
|
94
|
+
duration Integer
|
|
95
|
+
name String
|
|
96
|
+
id String
|
|
97
|
+
is_overnight [ TrueClass, FalseClass ], as: :is_overnight
|
|
98
|
+
end
|
|
99
|
+
|
|
100
|
+
class GoogleFlightsLayover < GoogleFlightsLayoverSchema
|
|
101
|
+
end
|
|
102
|
+
|
|
103
|
+
# Carbon emissions
|
|
104
|
+
GoogleFlightsCarbonEmissionsSchema = DynamicSchema::Struct.define do
|
|
105
|
+
this_flight Integer, as: :this_flight
|
|
106
|
+
typical_for_this_route Integer, as: :typical_for_this_route
|
|
107
|
+
difference_percent Integer, as: :difference_percent
|
|
108
|
+
lowest_route Integer, as: :lowest_route
|
|
109
|
+
end
|
|
110
|
+
|
|
111
|
+
class GoogleFlightsCarbonEmissions < GoogleFlightsCarbonEmissionsSchema
|
|
112
|
+
end
|
|
113
|
+
|
|
114
|
+
# Flight option
|
|
115
|
+
GoogleFlightsFlightSchema = DynamicSchema::Struct.define do
|
|
116
|
+
flights GoogleFlightsSegment, array: true
|
|
117
|
+
layovers GoogleFlightsLayover, array: true
|
|
118
|
+
total_duration Integer, as: :total_duration
|
|
119
|
+
carbon_emissions GoogleFlightsCarbonEmissions, as: :carbon_emissions
|
|
120
|
+
price Integer
|
|
121
|
+
type String
|
|
122
|
+
extensions String, array: true
|
|
123
|
+
airline_logo String, as: :airline_logo
|
|
124
|
+
booking_token String, as: :booking_token
|
|
125
|
+
departure_token String, as: :departure_token
|
|
126
|
+
end
|
|
127
|
+
|
|
128
|
+
class GoogleFlightsFlight < GoogleFlightsFlightSchema
|
|
129
|
+
end
|
|
130
|
+
|
|
131
|
+
# Price range
|
|
132
|
+
GoogleFlightsPriceRangeSchema = DynamicSchema::Struct.define do
|
|
133
|
+
low_price Integer, as: :low_price
|
|
134
|
+
high_price Integer, as: :high_price
|
|
135
|
+
end
|
|
136
|
+
|
|
137
|
+
class GoogleFlightsPriceRange < GoogleFlightsPriceRangeSchema
|
|
138
|
+
end
|
|
139
|
+
|
|
140
|
+
# Price history point
|
|
141
|
+
GoogleFlightsPriceHistorySchema = DynamicSchema::Struct.define do
|
|
142
|
+
price Integer
|
|
143
|
+
iso_date String, as: :iso_date
|
|
144
|
+
end
|
|
145
|
+
|
|
146
|
+
class GoogleFlightsPriceHistory < GoogleFlightsPriceHistorySchema
|
|
147
|
+
end
|
|
148
|
+
|
|
149
|
+
# Price insights
|
|
150
|
+
GoogleFlightsPriceInsightsSchema = DynamicSchema::Struct.define do
|
|
151
|
+
lowest_price Integer, as: :lowest_price
|
|
152
|
+
price_level String, as: :price_level
|
|
153
|
+
typical_price_range GoogleFlightsPriceRange, as: :typical_price_range
|
|
154
|
+
price_history GoogleFlightsPriceHistory, array: true, as: :price_history
|
|
155
|
+
end
|
|
156
|
+
|
|
157
|
+
class GoogleFlightsPriceInsights < GoogleFlightsPriceInsightsSchema
|
|
158
|
+
end
|
|
159
|
+
|
|
160
|
+
# Airport data
|
|
161
|
+
GoogleFlightsAirportDataInnerSchema = DynamicSchema::Struct.define do
|
|
162
|
+
id String
|
|
163
|
+
name String
|
|
164
|
+
end
|
|
165
|
+
|
|
166
|
+
class GoogleFlightsAirportDataInner < GoogleFlightsAirportDataInnerSchema
|
|
167
|
+
end
|
|
168
|
+
|
|
169
|
+
GoogleFlightsAirportDataSchema = DynamicSchema::Struct.define do
|
|
170
|
+
airport GoogleFlightsAirportDataInner
|
|
171
|
+
city String
|
|
172
|
+
country String
|
|
173
|
+
country_code String, as: :country_code
|
|
174
|
+
image String
|
|
175
|
+
thumbnail String
|
|
176
|
+
end
|
|
177
|
+
|
|
178
|
+
class GoogleFlightsAirportData < GoogleFlightsAirportDataSchema
|
|
179
|
+
end
|
|
180
|
+
|
|
181
|
+
# Airport info
|
|
182
|
+
GoogleFlightsAirportInfoSchema = DynamicSchema::Struct.define do
|
|
183
|
+
departure GoogleFlightsAirportData, array: true
|
|
184
|
+
arrival GoogleFlightsAirportData, array: true
|
|
185
|
+
end
|
|
186
|
+
|
|
187
|
+
class GoogleFlightsAirportInfo < GoogleFlightsAirportInfoSchema
|
|
188
|
+
end
|
|
189
|
+
|
|
190
|
+
# Booking request
|
|
191
|
+
GoogleFlightsBookingRequestSchema = DynamicSchema::Struct.define do
|
|
192
|
+
url String
|
|
193
|
+
post_data String, as: :post_data
|
|
194
|
+
end
|
|
195
|
+
|
|
196
|
+
class GoogleFlightsBookingRequest < GoogleFlightsBookingRequestSchema
|
|
197
|
+
end
|
|
198
|
+
|
|
199
|
+
# Local price
|
|
200
|
+
GoogleFlightsLocalPriceSchema = DynamicSchema::Struct.define do
|
|
201
|
+
currency String
|
|
202
|
+
price Integer
|
|
203
|
+
end
|
|
204
|
+
|
|
205
|
+
class GoogleFlightsLocalPrice < GoogleFlightsLocalPriceSchema
|
|
206
|
+
end
|
|
207
|
+
|
|
208
|
+
# Booking option
|
|
209
|
+
GoogleFlightsBookingOptionSchema = DynamicSchema::Struct.define do
|
|
210
|
+
book_with String, as: :book_with
|
|
211
|
+
airline_logos String, array: true, as: :airline_logos
|
|
212
|
+
flight_numbers String, array: true, as: :flight_numbers
|
|
213
|
+
price Integer
|
|
214
|
+
local_prices GoogleFlightsLocalPrice, array: true, as: :local_prices
|
|
215
|
+
option_title String, as: :option_title
|
|
216
|
+
extensions String, array: true
|
|
217
|
+
baggage_prices String, array: true, as: :baggage_prices
|
|
218
|
+
booking_phone String, as: :booking_phone
|
|
219
|
+
booking_request GoogleFlightsBookingRequest, as: :booking_request
|
|
220
|
+
is_split_booking [ TrueClass, FalseClass ], as: :is_split_booking
|
|
221
|
+
end
|
|
222
|
+
|
|
223
|
+
class GoogleFlightsBookingOption < GoogleFlightsBookingOptionSchema
|
|
224
|
+
end
|
|
225
|
+
|
|
226
|
+
# Selected flight
|
|
227
|
+
GoogleFlightsSelectedFlightSchema = DynamicSchema::Struct.define do
|
|
228
|
+
flights GoogleFlightsSegment, array: true
|
|
229
|
+
layovers GoogleFlightsLayover, array: true
|
|
230
|
+
total_duration Integer, as: :total_duration
|
|
231
|
+
carbon_emissions GoogleFlightsCarbonEmissions, as: :carbon_emissions
|
|
232
|
+
type String
|
|
233
|
+
airline_logo String, as: :airline_logo
|
|
234
|
+
end
|
|
235
|
+
|
|
236
|
+
class GoogleFlightsSelectedFlight < GoogleFlightsSelectedFlightSchema
|
|
237
|
+
end
|
|
238
|
+
|
|
239
|
+
# Main Google Flights result
|
|
240
|
+
GoogleFlightsResultSchema = DynamicSchema::Struct.define do
|
|
241
|
+
search_metadata GoogleFlightsMetadata, as: :search_metadata
|
|
242
|
+
search_parameters GoogleFlightsParameters, as: :search_parameters
|
|
243
|
+
best_flights GoogleFlightsFlight, array: true, as: :best_flights
|
|
244
|
+
other_flights GoogleFlightsFlight, array: true, as: :other_flights
|
|
245
|
+
price_insights GoogleFlightsPriceInsights, as: :price_insights
|
|
246
|
+
airports GoogleFlightsAirportInfo, array: true
|
|
247
|
+
selected_flights GoogleFlightsSelectedFlight, array: true, as: :selected_flights
|
|
248
|
+
booking_options GoogleFlightsBookingOption, array: true, as: :booking_options
|
|
249
|
+
error String
|
|
250
|
+
end
|
|
251
|
+
|
|
252
|
+
class GoogleFlightsResult < GoogleFlightsResultSchema
|
|
253
|
+
extend Forwardable
|
|
254
|
+
include Enumerable
|
|
255
|
+
|
|
256
|
+
def_delegators :best_flights, :each, :[], :count, :size, :length, :first, :last, :empty?
|
|
257
|
+
|
|
258
|
+
def success?
|
|
259
|
+
self.error.nil?
|
|
260
|
+
end
|
|
261
|
+
|
|
262
|
+
def all_flights
|
|
263
|
+
( best_flights || [] ) + ( other_flights || [] )
|
|
264
|
+
end
|
|
265
|
+
|
|
266
|
+
def cheapest
|
|
267
|
+
all_flights.min_by { | f | f.price || Float::INFINITY }
|
|
268
|
+
end
|
|
269
|
+
|
|
270
|
+
def fastest
|
|
271
|
+
all_flights.min_by { | f | f.total_duration || Float::INFINITY }
|
|
272
|
+
end
|
|
273
|
+
end
|
|
274
|
+
|
|
275
|
+
end
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
module SearchAPI
|
|
2
|
+
class GoogleImagesOptions
|
|
3
|
+
include DynamicSchema::Definable
|
|
4
|
+
include Helpers
|
|
5
|
+
|
|
6
|
+
DEVICES = %w[ desktop mobile tablet ]
|
|
7
|
+
SAFE_SEARCH = %w[ active off ]
|
|
8
|
+
SIZES = %w[ large medium icon larger_than_400x300 larger_than_640x480 larger_than_800x600
|
|
9
|
+
larger_than_1024x768 larger_than_2mp larger_than_4mp larger_than_6mp
|
|
10
|
+
larger_than_8mp larger_than_12mp larger_than_15mp larger_than_20mp
|
|
11
|
+
larger_than_40mp larger_than_70mp ]
|
|
12
|
+
COLORS = %w[ black_and_white color transparent red orange yellow green teal blue
|
|
13
|
+
purple pink white gray black brown ]
|
|
14
|
+
IMAGE_TYPES = %w[ clipart line_drawing gif face photo ]
|
|
15
|
+
TIME_PERIODS = %w[ last_hour last_day last_week last_month last_year ]
|
|
16
|
+
USAGE_RIGHTS = %w[ creative_commons_licenses commercial_or_other_licenses ]
|
|
17
|
+
ASPECT_RATIOS = %w[ square tall wide panoramic ]
|
|
18
|
+
|
|
19
|
+
NORMALIZE_DOWNCASE = ->(v) { v.to_s.downcase }
|
|
20
|
+
|
|
21
|
+
schema do
|
|
22
|
+
q String
|
|
23
|
+
device String, in: DEVICES, normalize: NORMALIZE_DOWNCASE
|
|
24
|
+
location String
|
|
25
|
+
uule String
|
|
26
|
+
google_domain String
|
|
27
|
+
gl String
|
|
28
|
+
hl String
|
|
29
|
+
lr String
|
|
30
|
+
cr String
|
|
31
|
+
nfpr Integer
|
|
32
|
+
filter Integer
|
|
33
|
+
safe String, in: SAFE_SEARCH, normalize: NORMALIZE_DOWNCASE
|
|
34
|
+
tbs String
|
|
35
|
+
size String, in: SIZES, normalize: NORMALIZE_DOWNCASE
|
|
36
|
+
color String, in: COLORS, normalize: NORMALIZE_DOWNCASE
|
|
37
|
+
image_type String, in: IMAGE_TYPES, normalize: NORMALIZE_DOWNCASE
|
|
38
|
+
time_period String, in: TIME_PERIODS, normalize: NORMALIZE_DOWNCASE
|
|
39
|
+
usage_rights String, in: USAGE_RIGHTS, normalize: NORMALIZE_DOWNCASE
|
|
40
|
+
aspect_ratio String, in: ASPECT_RATIOS, normalize: NORMALIZE_DOWNCASE
|
|
41
|
+
page Integer
|
|
42
|
+
end
|
|
43
|
+
|
|
44
|
+
def self.build( options = nil, &block )
|
|
45
|
+
new( api_options: builder.build( options, &block ) )
|
|
46
|
+
end
|
|
47
|
+
|
|
48
|
+
def self.build!( options = nil, &block )
|
|
49
|
+
new( api_options: builder.build!( options, &block ) )
|
|
50
|
+
end
|
|
51
|
+
|
|
52
|
+
def initialize( options = {}, api_options: nil )
|
|
53
|
+
@options = self.class.builder.build( options || {} )
|
|
54
|
+
@options = api_options.merge( @options ) if api_options
|
|
55
|
+
end
|
|
56
|
+
|
|
57
|
+
def to_h
|
|
58
|
+
result = @options.to_h
|
|
59
|
+
result[ :engine ] = 'google_images'
|
|
60
|
+
result
|
|
61
|
+
end
|
|
62
|
+
|
|
63
|
+
end
|
|
64
|
+
end
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
module SearchAPI
|
|
2
|
+
class GoogleImagesRequest < Request
|
|
3
|
+
|
|
4
|
+
def search( query, options = nil, &block )
|
|
5
|
+
if options
|
|
6
|
+
options = options.is_a?( GoogleImagesOptions ) ? options : GoogleImagesOptions.build!( options.to_h )
|
|
7
|
+
options = options.to_h
|
|
8
|
+
else
|
|
9
|
+
options = { engine: 'google_images' }
|
|
10
|
+
end
|
|
11
|
+
options[ :q ] = query.to_s
|
|
12
|
+
|
|
13
|
+
response = get( "#{ BASE_URI }/search", options, &block )
|
|
14
|
+
attributes = ( JSON.parse( response.body, symbolize_names: true ) rescue nil )
|
|
15
|
+
|
|
16
|
+
result = if response.success?
|
|
17
|
+
GoogleImagesResult.new( attributes || {} )
|
|
18
|
+
else
|
|
19
|
+
ErrorResult.new( response.status, attributes )
|
|
20
|
+
end
|
|
21
|
+
|
|
22
|
+
ResponseMethods.install( response, result )
|
|
23
|
+
end
|
|
24
|
+
|
|
25
|
+
end
|
|
26
|
+
end
|
|
@@ -0,0 +1,133 @@
|
|
|
1
|
+
require 'forwardable'
|
|
2
|
+
|
|
3
|
+
module SearchAPI
|
|
4
|
+
|
|
5
|
+
GoogleImagesMetadataSchema = DynamicSchema::Struct.define do
|
|
6
|
+
id String
|
|
7
|
+
status String
|
|
8
|
+
created_at String, as: :created_at
|
|
9
|
+
request_time_taken Float, as: :request_time_taken
|
|
10
|
+
parsing_time_taken Float, as: :parsing_time_taken
|
|
11
|
+
total_time_taken Float, as: :total_time_taken
|
|
12
|
+
request_url String, as: :request_url
|
|
13
|
+
html_url String, as: :html_url
|
|
14
|
+
json_url String, as: :json_url
|
|
15
|
+
end
|
|
16
|
+
|
|
17
|
+
class GoogleImagesMetadata < GoogleImagesMetadataSchema
|
|
18
|
+
end
|
|
19
|
+
|
|
20
|
+
GoogleImagesParametersSchema = DynamicSchema::Struct.define do
|
|
21
|
+
engine String
|
|
22
|
+
q String
|
|
23
|
+
device String
|
|
24
|
+
uule String
|
|
25
|
+
location String
|
|
26
|
+
location_used String, as: :location_used
|
|
27
|
+
cr String
|
|
28
|
+
google_domain String, as: :google_domain
|
|
29
|
+
hl String
|
|
30
|
+
gl String
|
|
31
|
+
lr String
|
|
32
|
+
nfpr Integer
|
|
33
|
+
filter Integer
|
|
34
|
+
safe String
|
|
35
|
+
page Integer
|
|
36
|
+
tbs String
|
|
37
|
+
chips String
|
|
38
|
+
size String
|
|
39
|
+
color String
|
|
40
|
+
image_type String, as: :image_type
|
|
41
|
+
time_period String, as: :time_period
|
|
42
|
+
usage_rights String, as: :usage_rights
|
|
43
|
+
aspect_ratio String, as: :aspect_ratio
|
|
44
|
+
next_page_token String, as: :next_page_token
|
|
45
|
+
end
|
|
46
|
+
|
|
47
|
+
class GoogleImagesParameters < GoogleImagesParametersSchema
|
|
48
|
+
end
|
|
49
|
+
|
|
50
|
+
GoogleImagesSearchInformationSchema = DynamicSchema::Struct.define do
|
|
51
|
+
query_displayed String, as: :query_displayed
|
|
52
|
+
total_results Integer, as: :total_results
|
|
53
|
+
page Integer
|
|
54
|
+
time_taken_displayed Float, as: :time_taken_displayed
|
|
55
|
+
detected_location String, as: :detected_location
|
|
56
|
+
did_you_mean String, as: :did_you_mean
|
|
57
|
+
has_no_results_for [ TrueClass, FalseClass ], as: :has_no_results_for
|
|
58
|
+
showing_results_for String, as: :showing_results_for
|
|
59
|
+
end
|
|
60
|
+
|
|
61
|
+
class GoogleImagesSearchInformation < GoogleImagesSearchInformationSchema
|
|
62
|
+
end
|
|
63
|
+
|
|
64
|
+
GoogleImagesSuggestionSchema = DynamicSchema::Struct.define do
|
|
65
|
+
title String
|
|
66
|
+
link String
|
|
67
|
+
thumbnail String
|
|
68
|
+
end
|
|
69
|
+
|
|
70
|
+
class GoogleImagesSuggestion < GoogleImagesSuggestionSchema
|
|
71
|
+
end
|
|
72
|
+
|
|
73
|
+
GoogleImagesSourceSchema = DynamicSchema::Struct.define do
|
|
74
|
+
name String
|
|
75
|
+
link String
|
|
76
|
+
end
|
|
77
|
+
|
|
78
|
+
class GoogleImagesSource < GoogleImagesSourceSchema
|
|
79
|
+
end
|
|
80
|
+
|
|
81
|
+
GoogleImagesOriginalSchema = DynamicSchema::Struct.define do
|
|
82
|
+
link String
|
|
83
|
+
width Integer
|
|
84
|
+
height Integer
|
|
85
|
+
end
|
|
86
|
+
|
|
87
|
+
class GoogleImagesOriginal < GoogleImagesOriginalSchema
|
|
88
|
+
end
|
|
89
|
+
|
|
90
|
+
GoogleImageSchema = DynamicSchema::Struct.define do
|
|
91
|
+
position Integer
|
|
92
|
+
title String
|
|
93
|
+
source GoogleImagesSource
|
|
94
|
+
original GoogleImagesOriginal
|
|
95
|
+
thumbnail String
|
|
96
|
+
tag String
|
|
97
|
+
end
|
|
98
|
+
|
|
99
|
+
class GoogleImage < GoogleImageSchema
|
|
100
|
+
end
|
|
101
|
+
|
|
102
|
+
GoogleImagesRelatedSearchSchema = DynamicSchema::Struct.define do
|
|
103
|
+
link String
|
|
104
|
+
query String
|
|
105
|
+
highlighted String, array: true
|
|
106
|
+
thumbnail String
|
|
107
|
+
end
|
|
108
|
+
|
|
109
|
+
class GoogleImagesRelatedSearch < GoogleImagesRelatedSearchSchema
|
|
110
|
+
end
|
|
111
|
+
|
|
112
|
+
GoogleImagesResultSchema = DynamicSchema::Struct.define do
|
|
113
|
+
search_metadata GoogleImagesMetadata, as: :search_metadata
|
|
114
|
+
search_parameters GoogleImagesParameters, as: :search_parameters
|
|
115
|
+
search_information GoogleImagesSearchInformation, as: :search_information
|
|
116
|
+
suggestions GoogleImagesSuggestion, array: true
|
|
117
|
+
images GoogleImage, array: true
|
|
118
|
+
related_searches GoogleImagesRelatedSearch, array: true, as: :related_searches
|
|
119
|
+
error String
|
|
120
|
+
end
|
|
121
|
+
|
|
122
|
+
class GoogleImagesResult < GoogleImagesResultSchema
|
|
123
|
+
extend Forwardable
|
|
124
|
+
include Enumerable
|
|
125
|
+
|
|
126
|
+
def_delegators :images, :each, :[], :count, :size, :length, :first, :last, :empty?
|
|
127
|
+
|
|
128
|
+
def success?
|
|
129
|
+
self.error.nil?
|
|
130
|
+
end
|
|
131
|
+
end
|
|
132
|
+
|
|
133
|
+
end
|
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
module SearchAPI
|
|
2
|
+
class GoogleLightOptions
|
|
3
|
+
include DynamicSchema::Definable
|
|
4
|
+
include Helpers
|
|
5
|
+
|
|
6
|
+
SAFE_SEARCH = %w[ active off ]
|
|
7
|
+
NORMALIZE_DOWNCASE = ->(v) { v.to_s.downcase }
|
|
8
|
+
|
|
9
|
+
schema do
|
|
10
|
+
q String
|
|
11
|
+
location String
|
|
12
|
+
uule String
|
|
13
|
+
google_domain String
|
|
14
|
+
hl String
|
|
15
|
+
gl String
|
|
16
|
+
lr String
|
|
17
|
+
nfpr String
|
|
18
|
+
filter String
|
|
19
|
+
safe String, in: SAFE_SEARCH, normalize: NORMALIZE_DOWNCASE
|
|
20
|
+
page Integer
|
|
21
|
+
end
|
|
22
|
+
|
|
23
|
+
def self.build( options = nil, &block )
|
|
24
|
+
new( api_options: builder.build( options, &block ) )
|
|
25
|
+
end
|
|
26
|
+
|
|
27
|
+
def self.build!( options = nil, &block )
|
|
28
|
+
new( api_options: builder.build!( options, &block ) )
|
|
29
|
+
end
|
|
30
|
+
|
|
31
|
+
def initialize( options = {}, api_options: nil )
|
|
32
|
+
@options = self.class.builder.build( options || {} )
|
|
33
|
+
@options = api_options.merge( @options ) if api_options
|
|
34
|
+
end
|
|
35
|
+
|
|
36
|
+
def to_h
|
|
37
|
+
result = @options.to_h
|
|
38
|
+
result[ :engine ] = 'google_light'
|
|
39
|
+
result
|
|
40
|
+
end
|
|
41
|
+
|
|
42
|
+
end
|
|
43
|
+
end
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
module SearchAPI
|
|
2
|
+
class GoogleLightRequest < Request
|
|
3
|
+
|
|
4
|
+
def search( query, options = nil, &block )
|
|
5
|
+
if options
|
|
6
|
+
options = options.is_a?( GoogleLightOptions ) ? options : GoogleLightOptions.build!( options.to_h )
|
|
7
|
+
options = options.to_h
|
|
8
|
+
else
|
|
9
|
+
options = { engine: 'google_light' }
|
|
10
|
+
end
|
|
11
|
+
options[ :q ] = query.to_s
|
|
12
|
+
|
|
13
|
+
response = get( "#{ BASE_URI }/search", options, &block )
|
|
14
|
+
attributes = ( JSON.parse( response.body, symbolize_names: true ) rescue nil )
|
|
15
|
+
|
|
16
|
+
result = if response.success?
|
|
17
|
+
GoogleLightResult.new( attributes || {} )
|
|
18
|
+
else
|
|
19
|
+
ErrorResult.new( response.status, attributes )
|
|
20
|
+
end
|
|
21
|
+
|
|
22
|
+
ResponseMethods.install( response, result )
|
|
23
|
+
end
|
|
24
|
+
|
|
25
|
+
end
|
|
26
|
+
end
|