diff --git a/README.md b/README.md index 98e988075f4aa5090909879f0191bf8fdb1369b2..aedb27669af97aba6dbff37333dcdaa86a7bc43c 100644 --- a/README.md +++ b/README.md @@ -509,6 +509,7 @@ The [Google Places Details API](https://developers.google.com/places/documentati #### Mapbox (`:mapbox`) * **API key**: required +* **Dataset**: Uses `mapbox.places` dataset by default. Specific the `mapbox.places-permanent` dataset by setting: `Geocoder.configure(:mapbox => {:dataset => "mapbox.places-permanent"})` * **Key signup**: https://www.mapbox.com/pricing/ * **Quota**: depends on plan * **Region**: complete coverage of US and Canada, partial coverage elsewhere (see for details: https://www.mapbox.com/developers/api/geocoding/#coverage) @@ -516,7 +517,7 @@ The [Google Places Details API](https://developers.google.com/places/documentati * **Languages**: English * **Documentation**: https://www.mapbox.com/developers/api/geocoding/ * **Terms of Service**: https://www.mapbox.com/tos/ -* **Limitations**: Must be displayed on a Mapbox map. Cache results for up to 30 days. +* **Limitations**: For `mapbox.places` dataset, must be displayed on a Mapbox map; Cache results for up to 30 days. For `mapbox.places-permanent` dataset, depends on plan. * **Notes**: Currently in public beta. #### Mapquest (`:mapquest`) diff --git a/lib/geocoder/lookups/mapbox.rb b/lib/geocoder/lookups/mapbox.rb index 8fa84884561b9a3a6251298bb876f3756859a251..797c2648b3fe14a20cc58ad822256a3d75194349 100644 --- a/lib/geocoder/lookups/mapbox.rb +++ b/lib/geocoder/lookups/mapbox.rb @@ -27,11 +27,16 @@ module Geocoder::Lookup def url_query_string(query) require 'cgi' unless defined?(CGI) && defined?(CGI.escape) - CGI.escape query.text.to_s + if query.reverse_geocode? + lat,lon = query.coordinates + "#{CGI.escape lon},#{CGI.escape lat}" + else + CGI.escape query.text.to_s + end end def dataset - "mapbox.places" + configuration[:dataset] || "mapbox.places" end def supported_protocols @@ -39,8 +44,9 @@ module Geocoder::Lookup end def sort_relevant_feature(features) + # Sort by descending relevance; Favor original order for equal relevance (eg occurs for reverse geocoding) features.sort_by do |feature| - feature["relevance"] + [feature["relevance"],-features.index(feature)] end.reverse end end diff --git a/lib/geocoder/results/mapbox.rb b/lib/geocoder/results/mapbox.rb index a948e75331cfc8a73d7de25a78e62595f46c002a..9142e1903668181928b854ccf79ab0a3bd2130fb 100644 --- a/lib/geocoder/results/mapbox.rb +++ b/lib/geocoder/results/mapbox.rb @@ -4,11 +4,11 @@ module Geocoder::Result class Mapbox < Base def latitude - @latitude ||= @data["geometry"]["coordinates"].first.to_f + @latitude ||= @data["geometry"]["coordinates"].last.to_f end def longitude - @longitude ||= @data["geometry"]["coordinates"].last.to_f + @longitude ||= @data["geometry"]["coordinates"].first.to_f end def coordinates diff --git a/test/unit/lookups/mapbox_test.rb b/test/unit/lookups/mapbox_test.rb index 688722d94c34ceb98c82b5f70c90916dc513a459..33d15924856546b2fe4b469877166cd6e25c6cc4 100644 --- a/test/unit/lookups/mapbox_test.rb +++ b/test/unit/lookups/mapbox_test.rb @@ -16,7 +16,7 @@ class MapboxTest < GeocoderTestCase def test_result_components result = Geocoder.search("Madison Square Garden, New York, NY").first - assert_equal [-73.991566, 40.749688], result.coordinates + assert_equal [40.749688, -73.991566], result.coordinates assert_equal "Madison Square Garden", result.place_name assert_equal "4 Penn Plz", result.street assert_equal "New York", result.city diff --git a/test/unit/result_test.rb b/test/unit/result_test.rb index 132e85bd5aa11138e2e8b5006f4575ef5c51068e..886f5dd5f610f9a79d78adea65faf091cd7d4690 100644 --- a/test/unit/result_test.rb +++ b/test/unit/result_test.rb @@ -12,6 +12,30 @@ class ResultTest < GeocoderTestCase end end + def test_result_has_coords_in_reasonable_range_for_madison_square_garden + Geocoder::Lookup.street_services.each do |l| + next unless File.exist?(File.join("test", "fixtures", "#{l.to_s}_madison_square_garden")) + Geocoder.configure(:lookup => l) + set_api_key!(l) + result = Geocoder.search("Madison Square Garden, New York, NY 10001, United States").first + assert (result.latitude > 40 and result.latitude < 41), "Lookup #{l} latitude out of range" + assert (result.longitude > -74 and result.longitude < -73), "Lookup #{l} longitude out of range" + end + end + + def test_result_accepts_reverse_coords_in_reasonable_range_for_madison_square_garden + Geocoder::Lookup.street_services.each do |l| + next unless File.exist?(File.join("test", "fixtures", "#{l.to_s}_madison_square_garden")) + next if [:bing, :esri, :geocoder_ca, :geocoder_us].include? l # Reverse fixture does not match forward + Geocoder.configure(:lookup => l) + set_api_key!(l) + result = Geocoder.search([40.750354, -73.993371]).first + assert (["New York", "New York City"].include? result.city), "Reverse lookup #{l} City does not match" + assert (result.latitude > 40 and result.latitude < 41), "Reverse lookup #{l} latitude out of range" + assert (result.longitude > -74 and result.longitude < -73), "Reverse lookup #{l} longitude out of range" + end + end + def test_yandex_result_without_city_does_not_raise_exception assert_nothing_raised do Geocoder.configure(:lookup => :yandex)