vpndetection 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.
Files changed (37) hide show
  1. checksums.yaml +7 -0
  2. data/LICENSE +21 -0
  3. data/README.md +171 -0
  4. data/lib/vpndetection/api/database_api.rb +351 -0
  5. data/lib/vpndetection/api/lookup_api.rb +85 -0
  6. data/lib/vpndetection/api_client.rb +397 -0
  7. data/lib/vpndetection/api_error.rb +58 -0
  8. data/lib/vpndetection/api_model_base.rb +88 -0
  9. data/lib/vpndetection/bogon.rb +60 -0
  10. data/lib/vpndetection/bogons.rb +67 -0
  11. data/lib/vpndetection/cache.rb +35 -0
  12. data/lib/vpndetection/client.rb +133 -0
  13. data/lib/vpndetection/configuration.rb +326 -0
  14. data/lib/vpndetection/database.rb +167 -0
  15. data/lib/vpndetection/errors.rb +107 -0
  16. data/lib/vpndetection/models/class_detail.rb +169 -0
  17. data/lib/vpndetection/models/dataset_checksums.rb +174 -0
  18. data/lib/vpndetection/models/dataset_checksums_response.rb +216 -0
  19. data/lib/vpndetection/models/dataset_format_size.rb +201 -0
  20. data/lib/vpndetection/models/dataset_list.rb +166 -0
  21. data/lib/vpndetection/models/dataset_metadata.rb +280 -0
  22. data/lib/vpndetection/models/dataset_metadata_column.rb +199 -0
  23. data/lib/vpndetection/models/download.rb +276 -0
  24. data/lib/vpndetection/models/download_list.rb +166 -0
  25. data/lib/vpndetection/models/error_envelope.rb +164 -0
  26. data/lib/vpndetection/models/licensed_dataset.rb +358 -0
  27. data/lib/vpndetection/models/licensed_version.rb +262 -0
  28. data/lib/vpndetection/models/lookup_error.rb +166 -0
  29. data/lib/vpndetection/models/lookup_response.rb +343 -0
  30. data/lib/vpndetection/models/proxy_detail.rb +199 -0
  31. data/lib/vpndetection/models/vpn_detail.rb +179 -0
  32. data/lib/vpndetection/result.rb +211 -0
  33. data/lib/vpndetection/retries.rb +33 -0
  34. data/lib/vpndetection/transport.rb +116 -0
  35. data/lib/vpndetection/version.rb +5 -0
  36. data/lib/vpndetection.rb +40 -0
  37. metadata +109 -0
@@ -0,0 +1,343 @@
1
+ =begin
2
+ #VPNDetection API
3
+
4
+ #The VPNDetection API: classify any IP address, and download the datasets behind the answers. See https://docs.vpndetection.io for guides and https://github.com/vpndetection-io for the official client libraries.
5
+
6
+ The version of the OpenAPI document: 2026.09.04
7
+ Contact: support@vpndetection.io
8
+ Generated by: https://openapi-generator.tech
9
+ Generator version: 7.25.0
10
+
11
+ =end
12
+
13
+ require 'date'
14
+ require 'time'
15
+
16
+ module VPNDetection
17
+ # The union of every plan's answer. Only `ip` and `is_vpn` are guaranteed; each remaining field is present when your plan includes it, and absent otherwise. A client that must work across plans should treat an absent flag as unknown rather than as `false`.
18
+ class LookupResponse < ApiModelBase
19
+ # The address that was looked up, normalized.
20
+ attr_accessor :ip
21
+
22
+ # Whether the address is VPN infrastructure. Keys off presence in the VPN dataset, so an unattributed range with no provider is still `true`.
23
+ attr_accessor :is_vpn
24
+
25
+ # Whether the address belongs to a hosting or cloud provider. Starter and above.
26
+ attr_accessor :is_hosting
27
+
28
+ # Whether the address is a privacy relay egress. Starter and above.
29
+ attr_accessor :is_relay
30
+
31
+ # Whether the address is a Tor node. Starter and above.
32
+ attr_accessor :is_tor
33
+
34
+ # Whether the address belongs to a CDN. Starter and above.
35
+ attr_accessor :is_cdn
36
+
37
+ # Whether the address was seen in a residential proxy pool. Max only.
38
+ attr_accessor :is_resproxy
39
+
40
+ # Whether the address was seen in a datacenter proxy pool. Max only.
41
+ attr_accessor :is_dcproxy
42
+
43
+ # Whether the address was seen in a mobile proxy pool. Max only.
44
+ attr_accessor :is_mobproxy
45
+
46
+ # Detail for `is_vpn`. Empty when `is_vpn` is false. Starter and above.
47
+ attr_accessor :vpn
48
+
49
+ # Detail for `is_hosting`. Empty when false. Scale and above.
50
+ attr_accessor :hosting
51
+
52
+ # Detail for `is_relay`. Empty when false. Scale and above.
53
+ attr_accessor :relay
54
+
55
+ # Detail for `is_tor`. Empty when false. Scale and above. The tor dataset carries no provider, so `provider` is always an empty string.
56
+ attr_accessor :tor
57
+
58
+ # Detail for `is_cdn`. Empty when false. Scale and above.
59
+ attr_accessor :cdn
60
+
61
+ # Detail for `is_resproxy`. Empty when false. Max only.
62
+ attr_accessor :resproxy
63
+
64
+ # Detail for `is_dcproxy`. Empty when false. Max only.
65
+ attr_accessor :dcproxy
66
+
67
+ # Detail for `is_mobproxy`. Empty when false. Max only.
68
+ attr_accessor :mobproxy
69
+
70
+ # Attribute mapping from ruby-style variable name to JSON key.
71
+ def self.attribute_map
72
+ {
73
+ :'ip' => :'ip',
74
+ :'is_vpn' => :'is_vpn',
75
+ :'is_hosting' => :'is_hosting',
76
+ :'is_relay' => :'is_relay',
77
+ :'is_tor' => :'is_tor',
78
+ :'is_cdn' => :'is_cdn',
79
+ :'is_resproxy' => :'is_resproxy',
80
+ :'is_dcproxy' => :'is_dcproxy',
81
+ :'is_mobproxy' => :'is_mobproxy',
82
+ :'vpn' => :'vpn',
83
+ :'hosting' => :'hosting',
84
+ :'relay' => :'relay',
85
+ :'tor' => :'tor',
86
+ :'cdn' => :'cdn',
87
+ :'resproxy' => :'resproxy',
88
+ :'dcproxy' => :'dcproxy',
89
+ :'mobproxy' => :'mobproxy'
90
+ }
91
+ end
92
+
93
+ # Returns attribute mapping this model knows about
94
+ def self.acceptable_attribute_map
95
+ attribute_map
96
+ end
97
+
98
+ # Returns all the JSON keys this model knows about
99
+ def self.acceptable_attributes
100
+ acceptable_attribute_map.values
101
+ end
102
+
103
+ # Attribute type mapping.
104
+ def self.openapi_types
105
+ {
106
+ :'ip' => :'String',
107
+ :'is_vpn' => :'Boolean',
108
+ :'is_hosting' => :'Boolean',
109
+ :'is_relay' => :'Boolean',
110
+ :'is_tor' => :'Boolean',
111
+ :'is_cdn' => :'Boolean',
112
+ :'is_resproxy' => :'Boolean',
113
+ :'is_dcproxy' => :'Boolean',
114
+ :'is_mobproxy' => :'Boolean',
115
+ :'vpn' => :'VpnDetail',
116
+ :'hosting' => :'ClassDetail',
117
+ :'relay' => :'ClassDetail',
118
+ :'tor' => :'ClassDetail',
119
+ :'cdn' => :'ClassDetail',
120
+ :'resproxy' => :'ProxyDetail',
121
+ :'dcproxy' => :'ProxyDetail',
122
+ :'mobproxy' => :'ProxyDetail'
123
+ }
124
+ end
125
+
126
+ # List of attributes with nullable: true
127
+ def self.openapi_nullable
128
+ Set.new([
129
+ ])
130
+ end
131
+
132
+ # Initializes the object
133
+ # @param [Hash] attributes Model attributes in the form of hash
134
+ def initialize(attributes = {})
135
+ if (!attributes.is_a?(Hash))
136
+ fail ArgumentError, "The input argument (attributes) must be a hash in `VPNDetection::LookupResponse` initialize method"
137
+ end
138
+
139
+ # check to see if the attribute exists and convert string to symbol for hash key
140
+ acceptable_attribute_map = self.class.acceptable_attribute_map
141
+ attributes = attributes.each_with_object({}) { |(k, v), h|
142
+ if (!acceptable_attribute_map.key?(k.to_sym))
143
+ fail ArgumentError, "`#{k}` is not a valid attribute in `VPNDetection::LookupResponse`. Please check the name to make sure it's valid. List of attributes: " + acceptable_attribute_map.keys.inspect
144
+ end
145
+ h[k.to_sym] = v
146
+ }
147
+
148
+ if attributes.key?(:'ip')
149
+ self.ip = attributes[:'ip']
150
+ else
151
+ self.ip = nil
152
+ end
153
+
154
+ if attributes.key?(:'is_vpn')
155
+ self.is_vpn = attributes[:'is_vpn']
156
+ else
157
+ self.is_vpn = nil
158
+ end
159
+
160
+ if attributes.key?(:'is_hosting')
161
+ self.is_hosting = attributes[:'is_hosting']
162
+ end
163
+
164
+ if attributes.key?(:'is_relay')
165
+ self.is_relay = attributes[:'is_relay']
166
+ end
167
+
168
+ if attributes.key?(:'is_tor')
169
+ self.is_tor = attributes[:'is_tor']
170
+ end
171
+
172
+ if attributes.key?(:'is_cdn')
173
+ self.is_cdn = attributes[:'is_cdn']
174
+ end
175
+
176
+ if attributes.key?(:'is_resproxy')
177
+ self.is_resproxy = attributes[:'is_resproxy']
178
+ end
179
+
180
+ if attributes.key?(:'is_dcproxy')
181
+ self.is_dcproxy = attributes[:'is_dcproxy']
182
+ end
183
+
184
+ if attributes.key?(:'is_mobproxy')
185
+ self.is_mobproxy = attributes[:'is_mobproxy']
186
+ end
187
+
188
+ if attributes.key?(:'vpn')
189
+ self.vpn = attributes[:'vpn']
190
+ end
191
+
192
+ if attributes.key?(:'hosting')
193
+ self.hosting = attributes[:'hosting']
194
+ end
195
+
196
+ if attributes.key?(:'relay')
197
+ self.relay = attributes[:'relay']
198
+ end
199
+
200
+ if attributes.key?(:'tor')
201
+ self.tor = attributes[:'tor']
202
+ end
203
+
204
+ if attributes.key?(:'cdn')
205
+ self.cdn = attributes[:'cdn']
206
+ end
207
+
208
+ if attributes.key?(:'resproxy')
209
+ self.resproxy = attributes[:'resproxy']
210
+ end
211
+
212
+ if attributes.key?(:'dcproxy')
213
+ self.dcproxy = attributes[:'dcproxy']
214
+ end
215
+
216
+ if attributes.key?(:'mobproxy')
217
+ self.mobproxy = attributes[:'mobproxy']
218
+ end
219
+ end
220
+
221
+ # Show invalid properties with the reasons. Usually used together with valid?
222
+ # @return Array for valid properties with the reasons
223
+ def list_invalid_properties
224
+ warn '[DEPRECATED] the `list_invalid_properties` method is obsolete'
225
+ invalid_properties = Array.new
226
+ if @ip.nil?
227
+ invalid_properties.push('invalid value for "ip", ip cannot be nil.')
228
+ end
229
+
230
+ if @is_vpn.nil?
231
+ invalid_properties.push('invalid value for "is_vpn", is_vpn cannot be nil.')
232
+ end
233
+
234
+ invalid_properties
235
+ end
236
+
237
+ # Check to see if the all the properties in the model are valid
238
+ # @return true if the model is valid
239
+ def valid?
240
+ warn '[DEPRECATED] the `valid?` method is obsolete'
241
+ return false if @ip.nil?
242
+ return false if @is_vpn.nil?
243
+ true
244
+ end
245
+
246
+ # Custom attribute writer method with validation
247
+ # @param [Object] ip Value to be assigned
248
+ def ip=(ip)
249
+ if ip.nil?
250
+ fail ArgumentError, 'ip cannot be nil'
251
+ end
252
+
253
+ @ip = ip
254
+ end
255
+
256
+ # Custom attribute writer method with validation
257
+ # @param [Object] is_vpn Value to be assigned
258
+ def is_vpn=(is_vpn)
259
+ if is_vpn.nil?
260
+ fail ArgumentError, 'is_vpn cannot be nil'
261
+ end
262
+
263
+ @is_vpn = is_vpn
264
+ end
265
+
266
+ # Checks equality by comparing each attribute.
267
+ # @param [Object] Object to be compared
268
+ def ==(o)
269
+ return true if self.equal?(o)
270
+ self.class == o.class &&
271
+ ip == o.ip &&
272
+ is_vpn == o.is_vpn &&
273
+ is_hosting == o.is_hosting &&
274
+ is_relay == o.is_relay &&
275
+ is_tor == o.is_tor &&
276
+ is_cdn == o.is_cdn &&
277
+ is_resproxy == o.is_resproxy &&
278
+ is_dcproxy == o.is_dcproxy &&
279
+ is_mobproxy == o.is_mobproxy &&
280
+ vpn == o.vpn &&
281
+ hosting == o.hosting &&
282
+ relay == o.relay &&
283
+ tor == o.tor &&
284
+ cdn == o.cdn &&
285
+ resproxy == o.resproxy &&
286
+ dcproxy == o.dcproxy &&
287
+ mobproxy == o.mobproxy
288
+ end
289
+
290
+ # @see the `==` method
291
+ # @param [Object] Object to be compared
292
+ def eql?(o)
293
+ self == o
294
+ end
295
+
296
+ # Calculates hash code according to all attributes.
297
+ # @return [Integer] Hash code
298
+ def hash
299
+ [ip, is_vpn, is_hosting, is_relay, is_tor, is_cdn, is_resproxy, is_dcproxy, is_mobproxy, vpn, hosting, relay, tor, cdn, resproxy, dcproxy, mobproxy].hash
300
+ end
301
+
302
+ # Builds the object from hash
303
+ # @param [Hash] attributes Model attributes in the form of hash
304
+ # @return [Object] Returns the model itself
305
+ def self.build_from_hash(attributes)
306
+ return nil unless attributes.is_a?(Hash)
307
+ attributes = attributes.transform_keys(&:to_sym)
308
+ transformed_hash = {}
309
+ openapi_types.each_pair do |key, type|
310
+ if attributes.key?(attribute_map[key]) && attributes[attribute_map[key]].nil?
311
+ transformed_hash["#{key}"] = nil
312
+ elsif type =~ /\AArray<(.*)>/i
313
+ # check to ensure the input is an array given that the attribute
314
+ # is documented as an array but the input is not
315
+ if attributes[attribute_map[key]].is_a?(Array)
316
+ transformed_hash["#{key}"] = attributes[attribute_map[key]].map { |v| _deserialize($1, v) }
317
+ end
318
+ elsif !attributes[attribute_map[key]].nil?
319
+ transformed_hash["#{key}"] = _deserialize(type, attributes[attribute_map[key]])
320
+ end
321
+ end
322
+ new(transformed_hash)
323
+ end
324
+
325
+ # Returns the object in the form of hash
326
+ # @return [Hash] Returns the object in the form of hash
327
+ def to_hash
328
+ hash = {}
329
+ self.class.attribute_map.each_pair do |attr, param|
330
+ value = self.send(attr)
331
+ if value.nil?
332
+ is_nullable = self.class.openapi_nullable.include?(attr)
333
+ next if !is_nullable || (is_nullable && !instance_variable_defined?(:"@#{attr}"))
334
+ end
335
+
336
+ hash[param] = _to_hash(value)
337
+ end
338
+ hash
339
+ end
340
+
341
+ end
342
+
343
+ end
@@ -0,0 +1,199 @@
1
+ =begin
2
+ #VPNDetection API
3
+
4
+ #The VPNDetection API: classify any IP address, and download the datasets behind the answers. See https://docs.vpndetection.io for guides and https://github.com/vpndetection-io for the official client libraries.
5
+
6
+ The version of the OpenAPI document: 2026.09.04
7
+ Contact: support@vpndetection.io
8
+ Generated by: https://openapi-generator.tech
9
+ Generator version: 7.25.0
10
+
11
+ =end
12
+
13
+ require 'date'
14
+ require 'time'
15
+
16
+ module VPNDetection
17
+ # The shared detail shape for the residential, datacenter and mobile proxy families, measured over a rolling 90 day window. Every key is present when the object is populated; the object is `{}` when its flag is false.
18
+ class ProxyDetail < ApiModelBase
19
+ # The proxy network, or an empty string where unattributed.
20
+ attr_accessor :provider
21
+
22
+ # The earliest date within the window this address was seen in the pool.
23
+ attr_accessor :first_seen
24
+
25
+ # The most recent date within the window this address was seen in the pool.
26
+ attr_accessor :last_seen
27
+
28
+ # How many times the address was observed in the pool during the window.
29
+ attr_accessor :hits
30
+
31
+ # The share of days in the window on which the address was seen, as a percentage. A high value means a stable pool member rather than a one-off sighting.
32
+ attr_accessor :hits_days_pct
33
+
34
+ # How many distinct proxy networks this address was seen in.
35
+ attr_accessor :providers_num
36
+
37
+ # Attribute mapping from ruby-style variable name to JSON key.
38
+ def self.attribute_map
39
+ {
40
+ :'provider' => :'provider',
41
+ :'first_seen' => :'first_seen',
42
+ :'last_seen' => :'last_seen',
43
+ :'hits' => :'hits',
44
+ :'hits_days_pct' => :'hits_days_pct',
45
+ :'providers_num' => :'providers_num'
46
+ }
47
+ end
48
+
49
+ # Returns attribute mapping this model knows about
50
+ def self.acceptable_attribute_map
51
+ attribute_map
52
+ end
53
+
54
+ # Returns all the JSON keys this model knows about
55
+ def self.acceptable_attributes
56
+ acceptable_attribute_map.values
57
+ end
58
+
59
+ # Attribute type mapping.
60
+ def self.openapi_types
61
+ {
62
+ :'provider' => :'String',
63
+ :'first_seen' => :'Date',
64
+ :'last_seen' => :'Date',
65
+ :'hits' => :'Integer',
66
+ :'hits_days_pct' => :'Integer',
67
+ :'providers_num' => :'Integer'
68
+ }
69
+ end
70
+
71
+ # List of attributes with nullable: true
72
+ def self.openapi_nullable
73
+ Set.new([
74
+ ])
75
+ end
76
+
77
+ # Initializes the object
78
+ # @param [Hash] attributes Model attributes in the form of hash
79
+ def initialize(attributes = {})
80
+ if (!attributes.is_a?(Hash))
81
+ fail ArgumentError, "The input argument (attributes) must be a hash in `VPNDetection::ProxyDetail` initialize method"
82
+ end
83
+
84
+ # check to see if the attribute exists and convert string to symbol for hash key
85
+ acceptable_attribute_map = self.class.acceptable_attribute_map
86
+ attributes = attributes.each_with_object({}) { |(k, v), h|
87
+ if (!acceptable_attribute_map.key?(k.to_sym))
88
+ fail ArgumentError, "`#{k}` is not a valid attribute in `VPNDetection::ProxyDetail`. Please check the name to make sure it's valid. List of attributes: " + acceptable_attribute_map.keys.inspect
89
+ end
90
+ h[k.to_sym] = v
91
+ }
92
+
93
+ if attributes.key?(:'provider')
94
+ self.provider = attributes[:'provider']
95
+ end
96
+
97
+ if attributes.key?(:'first_seen')
98
+ self.first_seen = attributes[:'first_seen']
99
+ end
100
+
101
+ if attributes.key?(:'last_seen')
102
+ self.last_seen = attributes[:'last_seen']
103
+ end
104
+
105
+ if attributes.key?(:'hits')
106
+ self.hits = attributes[:'hits']
107
+ end
108
+
109
+ if attributes.key?(:'hits_days_pct')
110
+ self.hits_days_pct = attributes[:'hits_days_pct']
111
+ end
112
+
113
+ if attributes.key?(:'providers_num')
114
+ self.providers_num = attributes[:'providers_num']
115
+ end
116
+ end
117
+
118
+ # Show invalid properties with the reasons. Usually used together with valid?
119
+ # @return Array for valid properties with the reasons
120
+ def list_invalid_properties
121
+ warn '[DEPRECATED] the `list_invalid_properties` method is obsolete'
122
+ invalid_properties = Array.new
123
+ invalid_properties
124
+ end
125
+
126
+ # Check to see if the all the properties in the model are valid
127
+ # @return true if the model is valid
128
+ def valid?
129
+ warn '[DEPRECATED] the `valid?` method is obsolete'
130
+ true
131
+ end
132
+
133
+ # Checks equality by comparing each attribute.
134
+ # @param [Object] Object to be compared
135
+ def ==(o)
136
+ return true if self.equal?(o)
137
+ self.class == o.class &&
138
+ provider == o.provider &&
139
+ first_seen == o.first_seen &&
140
+ last_seen == o.last_seen &&
141
+ hits == o.hits &&
142
+ hits_days_pct == o.hits_days_pct &&
143
+ providers_num == o.providers_num
144
+ end
145
+
146
+ # @see the `==` method
147
+ # @param [Object] Object to be compared
148
+ def eql?(o)
149
+ self == o
150
+ end
151
+
152
+ # Calculates hash code according to all attributes.
153
+ # @return [Integer] Hash code
154
+ def hash
155
+ [provider, first_seen, last_seen, hits, hits_days_pct, providers_num].hash
156
+ end
157
+
158
+ # Builds the object from hash
159
+ # @param [Hash] attributes Model attributes in the form of hash
160
+ # @return [Object] Returns the model itself
161
+ def self.build_from_hash(attributes)
162
+ return nil unless attributes.is_a?(Hash)
163
+ attributes = attributes.transform_keys(&:to_sym)
164
+ transformed_hash = {}
165
+ openapi_types.each_pair do |key, type|
166
+ if attributes.key?(attribute_map[key]) && attributes[attribute_map[key]].nil?
167
+ transformed_hash["#{key}"] = nil
168
+ elsif type =~ /\AArray<(.*)>/i
169
+ # check to ensure the input is an array given that the attribute
170
+ # is documented as an array but the input is not
171
+ if attributes[attribute_map[key]].is_a?(Array)
172
+ transformed_hash["#{key}"] = attributes[attribute_map[key]].map { |v| _deserialize($1, v) }
173
+ end
174
+ elsif !attributes[attribute_map[key]].nil?
175
+ transformed_hash["#{key}"] = _deserialize(type, attributes[attribute_map[key]])
176
+ end
177
+ end
178
+ new(transformed_hash)
179
+ end
180
+
181
+ # Returns the object in the form of hash
182
+ # @return [Hash] Returns the object in the form of hash
183
+ def to_hash
184
+ hash = {}
185
+ self.class.attribute_map.each_pair do |attr, param|
186
+ value = self.send(attr)
187
+ if value.nil?
188
+ is_nullable = self.class.openapi_nullable.include?(attr)
189
+ next if !is_nullable || (is_nullable && !instance_variable_defined?(:"@#{attr}"))
190
+ end
191
+
192
+ hash[param] = _to_hash(value)
193
+ end
194
+ hash
195
+ end
196
+
197
+ end
198
+
199
+ end