geocoder 1.4.3 → 1.4.4

Sign up to get free protection for your applications and to get access to all the features.

Potentially problematic release.


This version of geocoder might be problematic. Click here for more details.

checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: f394e733415900303ed8be35b91692886c134ffb
4
- data.tar.gz: 21211fb7e4b78a3f957923fabe959af3e9073c4f
3
+ metadata.gz: 7d93c7deeb30de425af22733c64e2a6297f610a4
4
+ data.tar.gz: 46c3d2b77ddb91bee2156bebebf102b73c1fd328
5
5
  SHA512:
6
- metadata.gz: 628aa577898b95b9a5674f2b8f97452c04744eebbe80af4a90372f5461bde24a217408dc5c06b2e99213907ee91e4beead63e51cf69e0631a1b6b42a7085e7f7
7
- data.tar.gz: fad11275dbbcc8a897b9d5b9231ceb543d0b81341745aaadd5033f93950af21cf04ea2bb93f0c8242d7c81a317b1eccf4be984d2b3bae9c3cb879b1fac02510a
6
+ metadata.gz: 327e8d5c40c31aa09be5b8e9d0b55ec18e74a8da166d0d65882fe31760182c4d96b36bfe3c0261cdeb2a5b91aefca204114d7bcc54dd46ea68e1cb7f0b7e3fd0
7
+ data.tar.gz: 5ad20ece66d7117b6e0928dd19daf8f602496a9b033fcf6833f58a0f6d9efd87388289681adf3a96a7c4ad71e159d7b06c956aca2e3646cdf8087bd4a570aec7
@@ -3,6 +3,11 @@ Changelog
3
3
 
4
4
  Major changes to Geocoder for each release. Please see the Git log for complete list of changes.
5
5
 
6
+ 1.4.4 (2017 May 17)
7
+ -------------------
8
+ * Use HTTPS by default for :freegeoip (thanks github.com/mehanoid).
9
+ * Add support for :amap lookup (thanks github.com/pzgz).
10
+
6
11
  1.4.3 (2017 Feb 7)
7
12
  -------------------
8
13
  * Add :google_places_search lookup (thanks github.com/waruboy).
data/README.md CHANGED
@@ -176,11 +176,11 @@ Some utility methods are also available:
176
176
  # look up coordinates of some location (like searching Google Maps)
177
177
  Geocoder.coordinates("25 Main St, Cooperstown, NY")
178
178
  => [42.700149, -74.922767]
179
-
179
+
180
180
  # distance between Eiffel Tower and Empire State Building
181
181
  Geocoder::Calculations.distance_between([47.858205,2.294359], [40.748433,-73.985655])
182
182
  => 3619.77359999382 # in configured units (default miles)
183
-
183
+
184
184
  # find the geographic center (aka center of gravity) of objects or points
185
185
  Geocoder::Calculations.geographic_center([city1, city2, [40.22,-73.99], city4])
186
186
  => [35.14968, -90.048929]
@@ -333,26 +333,26 @@ Some common configuration options are:
333
333
 
334
334
  # config/initializers/geocoder.rb
335
335
  Geocoder.configure(
336
-
336
+
337
337
  # geocoding service (see below for supported options):
338
338
  :lookup => :yandex,
339
-
339
+
340
340
  # IP address geocoding service (see below for supported options):
341
341
  :ip_lookup => :maxmind,
342
-
342
+
343
343
  # to use an API key:
344
344
  :api_key => "...",
345
-
345
+
346
346
  # geocoding service request timeout, in seconds (default 3):
347
347
  :timeout => 5,
348
-
348
+
349
349
  # set default units to kilometers:
350
350
  :units => :km,
351
-
351
+
352
352
  # caching (see below for details):
353
353
  :cache => Redis.new,
354
354
  :cache_prefix => "..."
355
-
355
+
356
356
  )
357
357
 
358
358
  Please see `lib/geocoder/configuration.rb` for a complete list of configuration options. Additionally, some lookups have their own configuration options, some of which are directly supported by Geocoder. For example, to specify a value for Google's `bounds` parameter:
@@ -375,21 +375,21 @@ You can also configure multiple geocoding services at once, like this:
375
375
 
376
376
  :timeout => 2,
377
377
  :cache => Redis.new,
378
-
378
+
379
379
  :yandex => {
380
380
  :api_key => "...",
381
381
  :timeout => 5
382
382
  },
383
-
383
+
384
384
  :baidu => {
385
385
  :api_key => "..."
386
386
  },
387
-
387
+
388
388
  :maxmind => {
389
389
  :api_key => "...",
390
390
  :service => :omni
391
391
  }
392
-
392
+
393
393
  )
394
394
 
395
395
  The above combines global and service-specific options and could be useful if you specify different geocoding services for different models or under different conditions. Lookup-specific settings override global settings. In the above example, the timeout for all lookups would be 2 seconds, except for Yandex which would be 5.
@@ -713,6 +713,18 @@ This uses the PostcodeAnywhere UK Geocode service, this will geocode any string
713
713
  * **Terms of Service**: https://adresse.data.gouv.fr/faq/ (in french)
714
714
  * **Limitations**: [Data licensed under Open Database License (ODbL) (you must provide attribution).](http://openstreetmap.fr/ban)
715
715
 
716
+ #### AMap (`:amap`)
717
+
718
+ - **API key**: required
719
+ - **Quota**: 2000/day and 2000/minute for personal developer, 4000000/day and 60000/minute for enterprise developer, for geocoding requests
720
+ - **Region**: China
721
+ - **SSL support**: yes
722
+ - **Languages**: Chinese (Simplified)
723
+ - **Documentation**: http://lbs.amap.com/api/webservice/guide/api/georegeo
724
+ - **Terms of Service**: http://lbs.amap.com/home/terms/
725
+ - **Limitations**: Only good for non-commercial use. For commercial usage please check http://lbs.amap.com/home/terms/
726
+ - **Notes**: To use AMap set `Geocoder.configure(:lookup => :amap, :api_key => "your_api_key")`.
727
+
716
728
  ### IP Address Services
717
729
 
718
730
  #### FreeGeoIP (`:freegeoip`)
@@ -835,7 +847,7 @@ You can generate ActiveRecord migrations and download and import data via provid
835
847
 
836
848
  # generate migration to create tables
837
849
  rails generate geocoder:maxmind:geolite_city
838
-
850
+
839
851
  # download, unpack, and import data
840
852
  rake geocoder:maxmind:geolite:load PACKAGE=city
841
853
 
@@ -884,6 +896,7 @@ This example uses Redis, but the cache store can be any object that supports the
884
896
  * `store#[](key)` or `#get` or `#read` - retrieves a value
885
897
  * `store#[]=(key, value)` or `#set` or `#write` - stores a value
886
898
  * `store#del(url)` - deletes a value
899
+ * `store#keys` - (Optional) Returns array of keys. Used if you wish to expire the entire cache (see below).
887
900
 
888
901
  Even a plain Ruby hash will work, though it's not a great choice (cleared out when app is restarted, not shared between app instances, etc).
889
902
 
@@ -923,7 +936,7 @@ For example:
923
936
 
924
937
  # build an address from street, city, and state attributes
925
938
  geocoded_by :address_from_components
926
-
939
+
927
940
  # store the fetched address in the full_address attribute
928
941
  reverse_geocoded_by :latitude, :longitude, :address => :full_address
929
942
  end
@@ -935,7 +948,7 @@ However, there can be only one set of latitude/longitude attributes, and whichev
935
948
  geocoded_by :address,
936
949
  :latitude => :fetched_latitude, # this will be overridden by the below
937
950
  :longitude => :fetched_longitude # same here
938
-
951
+
939
952
  reverse_geocoded_by :latitude, :longitude
940
953
  end
941
954
 
@@ -963,7 +976,7 @@ For example:
963
976
 
964
977
  after_validation :reverse_geocode, :if => :has_coordinates
965
978
  after_validation :geocode, :if => :has_location, :unless => :has_coordinates
966
-
979
+
967
980
  end
968
981
 
969
982
  Use Outside of Rails
@@ -1193,7 +1206,7 @@ Instead of using `includes` to reduce the number of database queries, try using
1193
1206
  # Pass a :select option to the near scope to get the columns you want.
1194
1207
  # Instead of City.near(...).includes(:venues), try:
1195
1208
  City.near("Omaha, NE", 20, :select => "cities.*, venues.*").joins(:venues)
1196
-
1209
+
1197
1210
  # This preload call will normally trigger two queries regardless of the
1198
1211
  # number of results; one query on hotels, and one query on administrators.
1199
1212
  # Instead of Hotel.near(...).includes(:administrator), try:
@@ -2,12 +2,13 @@ Geocoder.configure(
2
2
  # Geocoding options
3
3
  # timeout: 3, # geocoding service timeout (secs)
4
4
  # lookup: :google, # name of geocoding service (symbol)
5
+ # ip_lookup: :freegeoip, # name of IP address geocoding service (symbol)
5
6
  # language: :en, # ISO-639 language code
6
7
  # use_https: false, # use HTTPS for lookup requests? (if supported)
7
8
  # http_proxy: nil, # HTTP proxy server (user:pass@host:port)
8
9
  # https_proxy: nil, # HTTPS proxy server (user:pass@host:port)
9
10
  # api_key: nil, # API key for geocoding service
10
- # cache: nil, # cache object (must respond to #[], #[]=, and #keys)
11
+ # cache: nil, # cache object (must respond to #[], #[]=, and #del)
11
12
  # cache_prefix: 'geocoder:', # prefix (string) to use for all cache keys
12
13
 
13
14
  # Exceptions that should not be rescued by default
@@ -40,7 +40,11 @@ module Geocoder
40
40
  #
41
41
  def expire(url)
42
42
  if url == :all
43
- urls.each{ |u| expire(u) }
43
+ if store.respond_to?(:keys)
44
+ urls.each{ |u| expire(u) }
45
+ else
46
+ raise(NoMethodError, "The Geocoder cache store must implement `#keys` for `expire(:all)` to work")
47
+ end
44
48
  else
45
49
  expire_single_url(url)
46
50
  end
@@ -50,7 +50,8 @@ module Geocoder
50
50
  :geoportail_lu,
51
51
  :ban_data_gouv_fr,
52
52
  :test,
53
- :latlon
53
+ :latlon,
54
+ :amap
54
55
  ]
55
56
  end
56
57
 
@@ -0,0 +1,59 @@
1
+ require 'geocoder/lookups/base'
2
+ require "geocoder/results/amap"
3
+
4
+ module Geocoder::Lookup
5
+ class Amap < Base
6
+
7
+ def name
8
+ "AMap"
9
+ end
10
+
11
+ def required_api_key_parts
12
+ ["key"]
13
+ end
14
+
15
+ def query_url(query)
16
+ path = query.reverse_geocode? ? 'regeo' : 'geo'
17
+ "http://restapi.amap.com/v3/geocode/#{path}?" + url_query_string(query)
18
+ end
19
+
20
+ private # ---------------------------------------------------------------
21
+
22
+ def results(query, reverse = false)
23
+ return [] unless doc = fetch_data(query)
24
+ case [doc['status'], doc['info']]
25
+ when ['1', 'OK']
26
+ return doc['regeocodes'] unless doc['regeocodes'].blank?
27
+ return [doc['regeocode']] unless doc['regeocode'].blank?
28
+ return doc['geocodes'] unless doc['geocodes'].blank?
29
+ when ['0', 'INVALID_USER_KEY']
30
+ raise_error(Geocoder::InvalidApiKey, "invalid api key") ||
31
+ warn("#{self.name} Geocoding API error: invalid api key.")
32
+ else
33
+ raise_error(Geocoder::Error, "server error.") ||
34
+ warn("#{self.name} Geocoding API error: server error - [#{doc['info']}]")
35
+ end
36
+ return []
37
+ end
38
+
39
+ def query_url_params(query)
40
+ params = {
41
+ :key => configuration.api_key,
42
+ :output => "json"
43
+ }
44
+ if query.reverse_geocode?
45
+ params[:location] = revert_coordinates(query.text)
46
+ params[:extensions] = "all"
47
+ params[:coordsys] = "gps"
48
+ else
49
+ params[:address] = query.sanitized_text
50
+ end
51
+ params.merge(super)
52
+ end
53
+
54
+ def revert_coordinates(text)
55
+ [text[1],text[0]].join(",")
56
+ end
57
+
58
+ end
59
+ end
@@ -9,7 +9,12 @@ module Geocoder::Lookup
9
9
  end
10
10
 
11
11
  def supported_protocols
12
- [:http]
12
+ if configuration[:host]
13
+ [:http, :https]
14
+ else
15
+ # use https for default host
16
+ [:https]
17
+ end
13
18
  end
14
19
 
15
20
  def query_url(query)
@@ -1,3 +1,5 @@
1
+ require 'ipaddr'
2
+
1
3
  module Geocoder
2
4
  module Request
3
5
 
@@ -54,6 +56,8 @@ module Geocoder
54
56
  GEOCODER_CANDIDATE_HEADERS.each do |header|
55
57
  if @env.has_key? header
56
58
  addrs = geocoder_split_ip_addresses(@env[header])
59
+ addrs = geocoder_remove_port_from_addresses(addrs)
60
+ addrs = geocoder_reject_non_ipv4_addresses(addrs)
57
61
  addrs = geocoder_reject_trusted_ip_addresses(addrs)
58
62
  return addrs.first if addrs.any?
59
63
  end
@@ -75,6 +79,23 @@ module Geocoder
75
79
  def geocoder_reject_trusted_ip_addresses(ip_addresses)
76
80
  ip_addresses.reject { |ip| trusted_proxy?(ip) }
77
81
  end
82
+
83
+ def geocoder_remove_port_from_addresses(ip_addresses)
84
+ ip_addresses.map { |ip| ip.split(':').first }
85
+ end
86
+
87
+ def geocoder_reject_non_ipv4_addresses(ip_addresses)
88
+ ips = []
89
+ for ip in ip_addresses
90
+ begin
91
+ valid_ip = IPAddr.new(ip)
92
+ rescue
93
+ valid_ip = false
94
+ end
95
+ ips << valid_ip.to_s if valid_ip
96
+ end
97
+ return ips.any? ? ips : ip_addresses
98
+ end
78
99
  end
79
100
  end
80
101
 
@@ -0,0 +1,87 @@
1
+ require 'geocoder/results/base'
2
+
3
+ module Geocoder::Result
4
+ class Amap < Base
5
+
6
+ def coordinates
7
+ location = @data['location'] || @data['roadinters'].try(:first).try(:[], 'location') \
8
+ || address_components.try(:[], 'streetNumber').try(:[], 'location')
9
+ location.to_s.split(",").reverse.map(&:to_f)
10
+ end
11
+
12
+ def address
13
+ formatted_address
14
+ end
15
+
16
+ def state
17
+ province
18
+ end
19
+
20
+ def province
21
+ address_components['province']
22
+ end
23
+
24
+ def city
25
+ address_components['city'] == [] ? province : address_components["city"]
26
+ end
27
+
28
+ def district
29
+ address_components['district']
30
+ end
31
+
32
+ def street
33
+ if address_components["neighborhood"]["name"] != []
34
+ return address_components["neighborhood"]["name"]
35
+ elsif address_components['township'] != []
36
+ return address_components["township"]
37
+ else
38
+ return @data['street'] || address_components['streetNumber'].try(:[], 'street')
39
+ end
40
+ end
41
+
42
+ def street_number
43
+ @data['number'] || address_components['streetNumber'].try(:[], 'number')
44
+ end
45
+
46
+ def formatted_address
47
+ @data['formatted_address']
48
+ end
49
+
50
+ def address_components
51
+ @data['addressComponent'] || @data
52
+ end
53
+
54
+ def state_code
55
+ ""
56
+ end
57
+
58
+ def postal_code
59
+ ""
60
+ end
61
+
62
+ def country
63
+ "China"
64
+ end
65
+
66
+ def country_code
67
+ "CN"
68
+ end
69
+
70
+ ##
71
+ # Get address components of a given type. Valid types are defined in
72
+ # Baidu's Geocoding API documentation and include (among others):
73
+ #
74
+ # :business
75
+ # :cityCode
76
+ #
77
+ def self.response_attributes
78
+ %w[roads pois roadinters]
79
+ end
80
+
81
+ response_attributes.each do |a|
82
+ define_method a do
83
+ @data[a]
84
+ end
85
+ end
86
+ end
87
+ end
@@ -15,11 +15,15 @@ module Geocoder
15
15
  end
16
16
 
17
17
  def city
18
- data.fetch('city', {}).fetch('names', {}).fetch(locale, '')
18
+ fetch_name(
19
+ data.fetch('city', {}).fetch('names', {})
20
+ )
19
21
  end
20
22
 
21
23
  def state
22
- data.fetch('subdivisions', []).fetch(0, {}).fetch('names', {}).fetch(locale, '')
24
+ fetch_name(
25
+ data.fetch('subdivisions', []).fetch(0, {}).fetch('names', {})
26
+ )
23
27
  end
24
28
 
25
29
  def state_code
@@ -27,7 +31,9 @@ module Geocoder
27
31
  end
28
32
 
29
33
  def country
30
- data.fetch('country', {}).fetch('names', {}).fetch(locale, '')
34
+ fetch_name(
35
+ data.fetch('country', {}).fetch('names', {})
36
+ )
31
37
  end
32
38
 
33
39
  def country_code
@@ -48,14 +54,26 @@ module Geocoder
48
54
  end
49
55
  end
50
56
 
57
+ def language=(l)
58
+ @language = l.to_s
59
+ end
60
+
61
+ def language
62
+ @language ||= default_language
63
+ end
64
+
51
65
  private
52
66
 
53
67
  def data
54
68
  @data.to_hash
55
69
  end
56
70
 
57
- def locale
58
- @locale ||= Geocoder.config[:language].to_s
71
+ def default_language
72
+ @default_language = Geocoder.config[:language].to_s
73
+ end
74
+
75
+ def fetch_name(names)
76
+ names[language] || names[default_language] || ''
59
77
  end
60
78
  end
61
79
  end
@@ -17,6 +17,14 @@ module Geocoder::Result
17
17
  fail unless d = @data['Location']['DisplayPosition']
18
18
  [d['Latitude'].to_f, d['Longitude'].to_f]
19
19
  end
20
+
21
+ def route
22
+ address_data['Street']
23
+ end
24
+
25
+ def street_number
26
+ address_data['HouseNumber']
27
+ end
20
28
 
21
29
  def state
22
30
  address_data['County']
@@ -36,12 +36,13 @@ module Geocoder::Result
36
36
  @data['components']['village']
37
37
  end
38
38
 
39
-
40
39
  def state
41
40
  @data['components']['state']
42
41
  end
43
42
 
44
- alias_method :state_code, :state
43
+ def state_code
44
+ @data['components']['state_code']
45
+ end
45
46
 
46
47
  def postal_code
47
48
  @data['components']['postcode'].to_s
@@ -3,9 +3,15 @@ require 'geocoder/lookups/base'
3
3
  module Geocoder::Result
4
4
  class SmartyStreets < Base
5
5
  def coordinates
6
- %w(latitude longitude).map do |i|
6
+ result = %w(latitude longitude).map do |i|
7
7
  zipcode_endpoint? ? zipcodes.first[i] : metadata[i]
8
8
  end
9
+
10
+ if result.compact.empty?
11
+ nil
12
+ else
13
+ result
14
+ end
9
15
  end
10
16
 
11
17
  def address
@@ -1,3 +1,3 @@
1
1
  module Geocoder
2
- VERSION = "1.4.3"
2
+ VERSION = "1.4.4"
3
3
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: geocoder
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.4.3
4
+ version: 1.4.4
5
5
  platform: ruby
6
6
  authors:
7
7
  - Alex Reisner
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2017-02-07 00:00:00.000000000 Z
11
+ date: 2017-05-17 00:00:00.000000000 Z
12
12
  dependencies: []
13
13
  description: Provides object geocoding (by street or IP address), reverse geocoding
14
14
  (coordinates to street address), distance queries for ActiveRecord and Mongoid,
@@ -47,6 +47,7 @@ files:
47
47
  - lib/geocoder/kernel_logger.rb
48
48
  - lib/geocoder/logger.rb
49
49
  - lib/geocoder/lookup.rb
50
+ - lib/geocoder/lookups/amap.rb
50
51
  - lib/geocoder/lookups/baidu.rb
51
52
  - lib/geocoder/lookups/baidu_ip.rb
52
53
  - lib/geocoder/lookups/ban_data_gouv_fr.rb
@@ -94,6 +95,7 @@ files:
94
95
  - lib/geocoder/query.rb
95
96
  - lib/geocoder/railtie.rb
96
97
  - lib/geocoder/request.rb
98
+ - lib/geocoder/results/amap.rb
97
99
  - lib/geocoder/results/baidu.rb
98
100
  - lib/geocoder/results/baidu_ip.rb
99
101
  - lib/geocoder/results/ban_data_gouv_fr.rb
@@ -164,7 +166,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
164
166
  version: '0'
165
167
  requirements: []
166
168
  rubyforge_project:
167
- rubygems_version: 2.5.1
169
+ rubygems_version: 2.5.2
168
170
  signing_key:
169
171
  specification_version: 4
170
172
  summary: Complete geocoding solution for Ruby.