pepe-graticule 0.2.11

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 (88) hide show
  1. data/.gitignore +4 -0
  2. data/CHANGELOG.txt +61 -0
  3. data/LICENSE.txt +30 -0
  4. data/Manifest.txt +84 -0
  5. data/README.txt +41 -0
  6. data/Rakefile +143 -0
  7. data/VERSION +1 -0
  8. data/bin/geocode +5 -0
  9. data/graticule.gemspec +146 -0
  10. data/init.rb +2 -0
  11. data/lib/graticule.rb +26 -0
  12. data/lib/graticule/cli.rb +64 -0
  13. data/lib/graticule/core_ext.rb +15 -0
  14. data/lib/graticule/distance.rb +18 -0
  15. data/lib/graticule/distance/haversine.rb +40 -0
  16. data/lib/graticule/distance/spherical.rb +52 -0
  17. data/lib/graticule/distance/vincenty.rb +76 -0
  18. data/lib/graticule/geocoder.rb +21 -0
  19. data/lib/graticule/geocoder/base.rb +112 -0
  20. data/lib/graticule/geocoder/bogus.rb +15 -0
  21. data/lib/graticule/geocoder/geocoder_ca.rb +54 -0
  22. data/lib/graticule/geocoder/geocoder_us.rb +51 -0
  23. data/lib/graticule/geocoder/google.rb +100 -0
  24. data/lib/graticule/geocoder/host_ip.rb +41 -0
  25. data/lib/graticule/geocoder/local_search_maps.rb +45 -0
  26. data/lib/graticule/geocoder/mapquest.rb +87 -0
  27. data/lib/graticule/geocoder/meta_carta.rb +33 -0
  28. data/lib/graticule/geocoder/multi.rb +46 -0
  29. data/lib/graticule/geocoder/multimap.rb +73 -0
  30. data/lib/graticule/geocoder/postcode_anywhere.rb +63 -0
  31. data/lib/graticule/geocoder/rest.rb +18 -0
  32. data/lib/graticule/geocoder/yahoo.rb +84 -0
  33. data/lib/graticule/location.rb +82 -0
  34. data/lib/graticule/version.rb +9 -0
  35. data/site/index.html +114 -0
  36. data/site/plugin.html +82 -0
  37. data/site/stylesheets/style.css +69 -0
  38. data/test/config.yml.default +36 -0
  39. data/test/fixtures/responses/geocoder_us/success.xml +18 -0
  40. data/test/fixtures/responses/geocoder_us/unknown.xml +1 -0
  41. data/test/fixtures/responses/google/badkey.xml +1 -0
  42. data/test/fixtures/responses/google/limit.xml +10 -0
  43. data/test/fixtures/responses/google/missing_address.xml +1 -0
  44. data/test/fixtures/responses/google/only_coordinates.xml +1 -0
  45. data/test/fixtures/responses/google/partial.xml +1 -0
  46. data/test/fixtures/responses/google/server_error.xml +10 -0
  47. data/test/fixtures/responses/google/success.xml +1 -0
  48. data/test/fixtures/responses/google/success_multiple_results.xml +88 -0
  49. data/test/fixtures/responses/google/unavailable.xml +1 -0
  50. data/test/fixtures/responses/google/unknown_address.xml +1 -0
  51. data/test/fixtures/responses/host_ip/private.txt +4 -0
  52. data/test/fixtures/responses/host_ip/success.txt +4 -0
  53. data/test/fixtures/responses/host_ip/unknown.txt +4 -0
  54. data/test/fixtures/responses/local_search_maps/empty.txt +1 -0
  55. data/test/fixtures/responses/local_search_maps/not_found.txt +1 -0
  56. data/test/fixtures/responses/local_search_maps/success.txt +1 -0
  57. data/test/fixtures/responses/mapquest/multi_result.xml +1 -0
  58. data/test/fixtures/responses/mapquest/success.xml +1 -0
  59. data/test/fixtures/responses/meta_carta/bad_address.xml +17 -0
  60. data/test/fixtures/responses/meta_carta/multiple.xml +33 -0
  61. data/test/fixtures/responses/meta_carta/success.xml +31 -0
  62. data/test/fixtures/responses/multimap/missing_params.xml +4 -0
  63. data/test/fixtures/responses/multimap/no_matches.xml +4 -0
  64. data/test/fixtures/responses/multimap/success.xml +19 -0
  65. data/test/fixtures/responses/postcode_anywhere/badkey.xml +9 -0
  66. data/test/fixtures/responses/postcode_anywhere/canada.xml +16 -0
  67. data/test/fixtures/responses/postcode_anywhere/empty.xml +16 -0
  68. data/test/fixtures/responses/postcode_anywhere/success.xml +16 -0
  69. data/test/fixtures/responses/postcode_anywhere/uk.xml +18 -0
  70. data/test/fixtures/responses/yahoo/success.xml +3 -0
  71. data/test/fixtures/responses/yahoo/unknown_address.xml +6 -0
  72. data/test/mocks/uri.rb +52 -0
  73. data/test/test_helper.rb +31 -0
  74. data/test/unit/graticule/distance_test.rb +58 -0
  75. data/test/unit/graticule/geocoder/geocoder_us_test.rb +43 -0
  76. data/test/unit/graticule/geocoder/geocoders.rb +56 -0
  77. data/test/unit/graticule/geocoder/google_test.rb +112 -0
  78. data/test/unit/graticule/geocoder/host_ip_test.rb +40 -0
  79. data/test/unit/graticule/geocoder/local_search_maps_test.rb +30 -0
  80. data/test/unit/graticule/geocoder/mapquest_test.rb +47 -0
  81. data/test/unit/graticule/geocoder/meta_carta_test.rb +44 -0
  82. data/test/unit/graticule/geocoder/multi_test.rb +43 -0
  83. data/test/unit/graticule/geocoder/multimap_test.rb +52 -0
  84. data/test/unit/graticule/geocoder/postcode_anywhere_test.rb +50 -0
  85. data/test/unit/graticule/geocoder/yahoo_test.rb +48 -0
  86. data/test/unit/graticule/geocoder_test.rb +27 -0
  87. data/test/unit/graticule/location_test.rb +79 -0
  88. metadata +167 -0
@@ -0,0 +1,4 @@
1
+ <?xml version="1.0" encoding="UTF-8" ?>
2
+ <Results xmlns="http://clients.multimap.com/API" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
3
+ xsi:schemaLocation="http://clients.multimap.com/API http://clients.multimap.com/Schema/geocode_1.2.xsd"
4
+ errorCode="MM_GEOCODE_REQUIRED_PARAMETERS_MISSING" locationCount="0" />
@@ -0,0 +1,4 @@
1
+ <?xml version="1.0" encoding="UTF-8" ?>
2
+ <Results xmlns="http://clients.multimap.com/API" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
3
+ xsi:schemaLocation="http://clients.multimap.com/API http://clients.multimap.com/Schema/geocode_1.2.xsd"
4
+ errorCode="MM_GEOCODE_NO_MATCHES" locationCount="0" />
@@ -0,0 +1,19 @@
1
+ <?xml version="1.0" encoding="UTF-8" ?>
2
+ <Results xmlns="http://clients.multimap.com/API" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
3
+ xsi:schemaLocation="http://clients.multimap.com/API http://clients.multimap.com/Schema/geocode_1.2.xsd" locationCount="1">
4
+ <Location geocodeQuality="1">
5
+ <Address>
6
+ <Street>Oxford Street</Street>
7
+ <Areas>
8
+ <Area>LONDON</Area>
9
+ </Areas>
10
+ <PostalCode>W1</PostalCode>
11
+ <DisplayName>Oxford Street, LONDON, W1</DisplayName>
12
+ <CountryCode>GB</CountryCode>
13
+ </Address>
14
+ <Point>
15
+ <Lat>51.51452</Lat>
16
+ <Lon>-0.14839</Lon>
17
+ </Point>
18
+ </Location>
19
+ </Results>
@@ -0,0 +1,9 @@
1
+ <PostcodeAnywhere Server="WS12" Version="3.0" Date="12/03/2007 15:43:33" Duration="0.016s">
2
+ <Schema Items="2">
3
+ <Field Name="error_number"/>
4
+ <Field Name="message"/>
5
+ </Schema>
6
+ <Data Items="1">
7
+ <Item error_number="6" message="License key was not recognised"/>
8
+ </Data>
9
+ </PostcodeAnywhere>
@@ -0,0 +1,16 @@
1
+ <?xml version="1.0" encoding="UTF-8"?>
2
+ <PostcodeAnywhere Server="WS12" Version="3.0" Date="17/03/2007 19:01:05" Duration="1.109s">
3
+ <Schema Items="8">
4
+ <Field Name="line1"/>
5
+ <Field Name="line2"/>
6
+ <Field Name="city"/>
7
+ <Field Name="state"/>
8
+ <Field Name="postal_code"/>
9
+ <Field Name="country"/>
10
+ <Field Name="longitude"/>
11
+ <Field Name="latitude"/>
12
+ </Schema>
13
+ <Data Items="1">
14
+ <Item line1="204 Campbell Ave" city="Revelstoke" state="BC" postal_code="V0E" country="Canada" longitude="-118.196970002204" latitude="50.9997350418267"/>
15
+ </Data>
16
+ </PostcodeAnywhere>
@@ -0,0 +1,16 @@
1
+ <?xml version="1.0" encoding="UTF-8"?>
2
+ <PostcodeAnywhere Version="3.0" Server="WS03" Date="17/03/2007 19:26:33" Duration="0.016s">
3
+ <Schema Items="10">
4
+ <Field Name="id"/>
5
+ <Field Name="seq"/>
6
+ <Field Name="location"/>
7
+ <Field Name="grid_east_m"/>
8
+ <Field Name="grid_north_m"/>
9
+ <Field Name="longitude"/>
10
+ <Field Name="latitude"/>
11
+ <Field Name="os_reference"/>
12
+ <Field Name="wgs84_longitude"/>
13
+ <Field Name="wgs84_latitude"/>
14
+ </Schema>
15
+ <Data Items="0"/>
16
+ </PostcodeAnywhere>
@@ -0,0 +1,16 @@
1
+ <?xml version="1.0" encoding="UTF-8"?>
2
+ <PostcodeAnywhere Server="WS11" Version="3.0" Date="17/03/2007 18:12:11" Duration="1.703s">
3
+ <Schema Items="8">
4
+ <Field Name="line1"/>
5
+ <Field Name="line2"/>
6
+ <Field Name="city"/>
7
+ <Field Name="state"/>
8
+ <Field Name="postal_code"/>
9
+ <Field Name="country"/>
10
+ <Field Name="longitude"/>
11
+ <Field Name="latitude"/>
12
+ </Schema>
13
+ <Data Items="1">
14
+ <Item line1="204 Campbell Ave" city="Revelstoke" state="BC" postal_code="V0E" country="Canada" longitude="-118.196970002204" latitude="50.9997350418267"/>
15
+ </Data>
16
+ </PostcodeAnywhere>
@@ -0,0 +1,18 @@
1
+ <?xml version="1.0" encoding="UTF-8"?>
2
+ <PostcodeAnywhere Server="WS12" Version="3.0" Date="17/03/2007 19:01:39" Duration="2.422s">
3
+ <Schema Items="10">
4
+ <Field Name="id"/>
5
+ <Field Name="seq"/>
6
+ <Field Name="location"/>
7
+ <Field Name="grid_east_m"/>
8
+ <Field Name="grid_north_m"/>
9
+ <Field Name="longitude"/>
10
+ <Field Name="latitude"/>
11
+ <Field Name="os_reference"/>
12
+ <Field Name="wgs84_longitude"/>
13
+ <Field Name="wgs84_latitude"/>
14
+ </Schema>
15
+ <Data Items="1">
16
+ <Item id="17783983.00" seq="0" location="80 Wood Lane London NW9" grid_east_m="521000" grid_north_m="187500" longitude="-0.253788666693255" latitude="51.5728910186362" os_reference="TQ 21000 87500" wgs84_longitude="-0.255365891581496" wgs84_latitude="51.5733397173092"/>
17
+ </Data>
18
+ </PostcodeAnywhere>
@@ -0,0 +1,3 @@
1
+ <?xml version="1.0"?>
2
+ <ResultSet xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="urn:yahoo:maps" xsi:schemaLocation="urn:yahoo:maps http://api.local.yahoo.com/MapsService/V1/GeocodeResponse.xsd"><Result precision="address" warning="The exact location could not be found, here is the closest match: 701 First Ave, Sunnyvale, CA 94089"><Latitude>37.416384</Latitude><Longitude>-122.024853</Longitude><Address>701 FIRST AVE</Address><City>SUNNYVALE</City><State>CA</State><Zip>94089-1019</Zip><Country>US</Country></Result></ResultSet>
3
+ <!-- ws06.search.re2.yahoo.com uncompressed/chunked Wed Apr 25 15:13:01 PDT 2007 -->
@@ -0,0 +1,6 @@
1
+ <?xml version="1.0" encoding="UTF-8"?>
2
+ <Error xmlns="urn:yahoo:api">
3
+ The following errors were detected:
4
+ <Message>unable to parse location</Message>
5
+ </Error>
6
+ <!-- ws05.search.re2.yahoo.com uncompressed/chunked Wed Apr 25 15:13:01 PDT 2007 -->
data/test/mocks/uri.rb ADDED
@@ -0,0 +1,52 @@
1
+ require 'uri/http'
2
+ require 'open-uri'
3
+
4
+ ##
5
+ # This stub overrides OpenURI's open method to allow programs that use OpenURI
6
+ # to be easily tested.
7
+ #
8
+ # == Usage
9
+ #
10
+ # require 'rc_rest/uri_stub'
11
+ #
12
+ # class TestMyClass < Test::Unit::TestCase
13
+ #
14
+ # def setup
15
+ # URI::HTTP.responses = []
16
+ # URI::HTTP.uris = []
17
+ #
18
+ # @obj = MyClass.new
19
+ # end
20
+ #
21
+ # def test_my_method
22
+ # URI::HTTP.responses << 'some text open would ordinarily return'
23
+ #
24
+ # result = @obj.my_method
25
+ #
26
+ # assert_equal :something_meaninfgul, result
27
+ #
28
+ # assert_equal true, URI::HTTP.responses.empty?
29
+ # assert_equal 1, URI::HTTP.uris.length
30
+ # assert_equal 'http://example.com/path', URI::HTTP.uris.first
31
+ # end
32
+ #
33
+ # end
34
+
35
+ class URI::HTTP # :nodoc:
36
+
37
+ class << self
38
+ attr_accessor :responses, :uris
39
+ end
40
+
41
+ alias original_open open
42
+
43
+ def open(*args)
44
+ self.class.uris << self.to_s
45
+ io = StringIO.new(self.class.responses.shift)
46
+ OpenURI::Meta.init(io)
47
+ yield io if block_given?
48
+ io
49
+ end
50
+
51
+ end
52
+
@@ -0,0 +1,31 @@
1
+ $:.unshift(File.dirname(__FILE__) + '/../lib')
2
+ $:.unshift(File.dirname(__FILE__) + '/mocks')
3
+
4
+ require 'rubygems'
5
+ require 'yaml'
6
+ require 'test/unit'
7
+ require 'graticule'
8
+ require 'mocha'
9
+
10
+ TEST_RESPONSE_PATH = File.dirname(__FILE__) + '/fixtures/responses'
11
+
12
+ module Test
13
+ module Unit
14
+ module Assertions
15
+
16
+ private
17
+ def response(geocoder, response, extension = 'xml')
18
+ clean_backtrace do
19
+ File.read(File.dirname(__FILE__) + "/fixtures/responses/#{geocoder}/#{response}.#{extension}")
20
+ end
21
+ end
22
+
23
+ def clean_backtrace(&block)
24
+ yield
25
+ rescue AssertionFailedError => e
26
+ path = File.expand_path(__FILE__)
27
+ raise AssertionFailedError, e.message, e.backtrace.reject { |line| File.expand_path(line) =~ /#{path}/ }
28
+ end
29
+ end
30
+ end
31
+ end
@@ -0,0 +1,58 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/../../test_helper')
2
+
3
+ module Graticule
4
+ module Distance
5
+ class DistanceFormulaTest < Test::Unit::TestCase
6
+ EARTH_RADIUS_IN_MILES = 3963.1676
7
+ EARTH_RADIUS_IN_KILOMETERS = 6378.135
8
+
9
+ FORMULAS = [Haversine, Spherical, Vincenty]
10
+
11
+ def test_earth_radius
12
+ assert_equal EARTH_RADIUS_IN_MILES, EARTH_RADIUS[:miles]
13
+ assert_equal EARTH_RADIUS_IN_KILOMETERS, EARTH_RADIUS[:kilometers]
14
+ end
15
+
16
+ def test_distance
17
+ washington_dc = Location.new(:latitude => 38.898748, :longitude => -77.037684)
18
+ chicago = Location.new(:latitude => 41.85, :longitude => -87.65)
19
+
20
+ FORMULAS.each do |formula|
21
+ assert_in_delta formula.distance(washington_dc, chicago), formula.distance(chicago, washington_dc), 0.00001
22
+ assert_in_delta 594.820, formula.distance(washington_dc, chicago), 1.0
23
+ assert_in_delta 594.820, formula.distance(washington_dc, chicago, :miles), 1.0
24
+ assert_in_delta 957.275, formula.distance(washington_dc, chicago, :kilometers), 1.0
25
+ end
26
+ end
27
+
28
+ def test_distance_between_antipodal_points
29
+ # The Vincenty formula will be indeterminant with antipodal points.
30
+ # See http://mathworld.wolfram.com/AntipodalPoints.html
31
+ washington_dc = Location.new(:latitude => 38.898748, :longitude => -77.037684)
32
+ chicago = Location.new(:latitude => 41.85, :longitude => -87.65)
33
+
34
+ # First, test the deltas.
35
+ FORMULAS.each do |formula|
36
+ assert_in_delta 12450.6582171051,
37
+ formula.distance(chicago, chicago.antipodal_location), 1.0
38
+ assert_in_delta 12450.6582171051,
39
+ formula.distance(washington_dc, washington_dc.antipodal_location), 1.0
40
+ assert_in_delta 12450.6582171051,
41
+ formula.distance(chicago, chicago.antipodal_location, :miles), 1.0
42
+ assert_in_delta 12450.6582171051,
43
+ formula.distance(washington_dc, washington_dc.antipodal_location, :miles), 1.0
44
+ assert_in_delta 20037.50205960391,
45
+ formula.distance(chicago, chicago.antipodal_location, :kilometers), 1.0
46
+ assert_in_delta 20037.5020596039,
47
+ formula.distance(washington_dc, washington_dc.antipodal_location, :kilometers), 1.0
48
+ end
49
+
50
+ # Next, test Vincenty. Vincenty will use haversine instead of returning NaN on antipodal points
51
+ assert_equal Haversine.distance(washington_dc, washington_dc.antipodal_location),
52
+ Vincenty.distance(washington_dc, washington_dc.antipodal_location)
53
+ assert_equal Haversine.distance(chicago, chicago.antipodal_location),
54
+ Vincenty.distance(chicago, chicago.antipodal_location)
55
+ end
56
+ end
57
+ end
58
+ end
@@ -0,0 +1,43 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/../../../test_helper')
2
+
3
+ module Graticule
4
+ module Geocoder
5
+ class GeocoderUsTest < Test::Unit::TestCase
6
+
7
+ def setup
8
+ URI::HTTP.responses = []
9
+ URI::HTTP.uris = []
10
+
11
+ @geocoder = GeocoderUs.new
12
+ @location = Location.new(
13
+ :street => "1600 Pennsylvania Ave NW, Washington DC 20502",
14
+ :longitude => -77.037684,
15
+ :latitude => 38.898748
16
+ )
17
+ end
18
+
19
+ def test_success
20
+ prepare_response(:success)
21
+ assert_equal @location, @geocoder.locate('1600 Pennsylvania Ave, Washington DC')
22
+ end
23
+
24
+ def test_url
25
+ prepare_response(:success)
26
+ @geocoder.locate('1600 Pennsylvania Ave, Washington DC')
27
+ assert_equal 'http://rpc.geocoder.us/service/rest/geocode?address=1600%20Pennsylvania%20Ave,%20Washington%20DC',
28
+ URI::HTTP.uris.first
29
+ end
30
+
31
+ def test_locate_bad_address
32
+ prepare_response(:unknown)
33
+ assert_raises(AddressError) { @geocoder.locate('yuck') }
34
+ end
35
+
36
+ protected
37
+ def prepare_response(id)
38
+ URI::HTTP.responses << response('geocoder_us', id)
39
+ end
40
+
41
+ end
42
+ end
43
+ end
@@ -0,0 +1,56 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/../../../test_helper')
2
+
3
+
4
+ module Graticule
5
+
6
+ # Generic tests for all geocoders (theoretically)
7
+ module GeocodersTestCase
8
+
9
+ def test_success
10
+ return unless prepare_response(:success)
11
+
12
+ location = Location.new(
13
+ :street => "1600 Amphitheatre Pkwy",
14
+ :city => "Mountain View",
15
+ :state => "CA",
16
+ :zip => "94043",
17
+ :country => "US",
18
+ :longitude => -122.083739,
19
+ :latitude => 37.423021,
20
+ :precision => :address
21
+ )
22
+ assert_equal location, @geocoder.locate('1600 Amphitheatre Parkway, Mountain View, CA')
23
+ end
24
+
25
+ def test_bad_key
26
+ return unless prepare_response(:badkey)
27
+ assert_raises(CredentialsError) { @geocoder.locate('x') }
28
+ end
29
+
30
+ def test_locate_missing_address
31
+ return unless prepare_response(:missing_address)
32
+ assert_raises(AddressError) { @geocoder.locate 'x' }
33
+ end
34
+
35
+ def test_locate_server_error
36
+ return unless prepare_response(:server_error)
37
+ assert_raises(Error) { @geocoder.locate 'x' }
38
+ end
39
+
40
+ def test_locate_too_many_queries
41
+ return unless prepare_response(:limit)
42
+ assert_raises(CredentialsError) { @geocoder.locate 'x' }
43
+ end
44
+
45
+ def test_locate_unavailable_address
46
+ return unless prepare_response(:unavailable)
47
+ assert_raises(AddressError) { @geocoder.locate 'x' }
48
+ end
49
+
50
+ def test_locate_unknown_address
51
+ return unless prepare_response(:unknown_address)
52
+ assert_raises(AddressError) { @geocoder.locate 'x' }
53
+ end
54
+
55
+ end
56
+ end
@@ -0,0 +1,112 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/../../../test_helper')
2
+
3
+ module Graticule
4
+ module Geocoder
5
+ class GoogleTest < Test::Unit::TestCase
6
+ def setup
7
+ URI::HTTP.responses = []
8
+ URI::HTTP.uris = []
9
+ @geocoder = Google.new(:key => 'APP_ID')
10
+ end
11
+
12
+ def test_success
13
+ return unless prepare_response(:success)
14
+
15
+ location = Location.new(
16
+ :street => "1600 Amphitheatre Pkwy",
17
+ :locality => "Mountain View",
18
+ :region => "CA",
19
+ :postal_code => "94043",
20
+ :country => "US",
21
+ :longitude => -122.083739,
22
+ :latitude => 37.423021,
23
+ :precision => :address
24
+ )
25
+ assert_equal location, @geocoder.locate('1600 Amphitheatre Parkway, Mountain View, CA')
26
+ end
27
+
28
+
29
+ # The #locate parameters are broad, so the XML response contains
30
+ # multiple results at street-level precision. We expect to get the
31
+ # first result back, and it should not contain a postal code.
32
+ def test_success_multiple_results
33
+ return unless prepare_response(:success_multiple_results)
34
+
35
+ location = Location.new(
36
+ :street => "Queen St W",
37
+ :locality => "Toronto",
38
+ :region => "ON",
39
+ :postal_code => nil,
40
+ :country => "CA",
41
+ :longitude => -79.4125590,
42
+ :latitude => 43.6455030,
43
+ :precision => :street
44
+ )
45
+ assert_equal location, @geocoder.locate('Queen St West, Toronto, ON CA')
46
+ end
47
+
48
+
49
+ # <?xml version='1.0' encoding='UTF-8'?><kml xmlns='http://earth.google.com/kml/2.0'><Response><name>15-17 </name><Status><code>200</code><request>geocode</request></Status><Placemark id='p1'><Point><coordinates>-17.000000,15.000000,0</coordinates></Point></Placemark></Response></kml>
50
+ def test_only_coordinates
51
+ return unless prepare_response(:only_coordinates)
52
+
53
+ location = Location.new(:longitude => -17.000000, :latitude => 15.000000)
54
+ assert_equal location, @geocoder.locate('15-17 & 16 Railroad Square, Nashua, NH, 03064')
55
+ end
56
+
57
+
58
+
59
+ def test_partial
60
+ return unless prepare_response(:partial)
61
+
62
+ location = Location.new(
63
+ :locality => "San Francisco",
64
+ :region => "CA",
65
+ :country => "US",
66
+ :longitude => -122.418333,
67
+ :latitude => 37.775000,
68
+ :precision => :city
69
+ )
70
+
71
+ assert_equal location, @geocoder.locate('sf ca')
72
+ end
73
+
74
+ def test_bad_key
75
+ return unless prepare_response(:badkey)
76
+ assert_raises(CredentialsError) { @geocoder.locate('x') }
77
+ end
78
+
79
+ def test_locate_missing_address
80
+ return unless prepare_response(:missing_address)
81
+ assert_raises(AddressError) { @geocoder.locate 'x' }
82
+ end
83
+
84
+ def test_locate_server_error
85
+ return unless prepare_response(:server_error)
86
+ assert_raises(Error) { @geocoder.locate 'x' }
87
+ end
88
+
89
+ def test_locate_too_many_queries
90
+ return unless prepare_response(:limit)
91
+ assert_raises(CredentialsError) { @geocoder.locate 'x' }
92
+ end
93
+
94
+ def test_locate_unavailable_address
95
+ return unless prepare_response(:unavailable)
96
+ assert_raises(AddressError) { @geocoder.locate 'x' }
97
+ end
98
+
99
+ def test_locate_unknown_address
100
+ return unless prepare_response(:unknown_address)
101
+ assert_raises(AddressError) { @geocoder.locate 'x' }
102
+ end
103
+
104
+ protected
105
+
106
+ def prepare_response(id = :success)
107
+ URI::HTTP.responses << response('google', id)
108
+ end
109
+
110
+ end
111
+ end
112
+ end