From a1763f7a005512ed63030531355cf73695b799df Mon Sep 17 00:00:00 2001
From: Alex Reisner <alex@alexreisner.com>
Date: Mon, 7 Mar 2011 23:35:04 -0500
Subject: [PATCH] Don't try to look up loopback IP address.

Detect this at the Lookup level (instead of the Rack::Request level, for
example) and return the response we know Freegeoip.net will give.
---
 lib/geocoder/lookups/base.rb      |  7 +++++++
 lib/geocoder/lookups/freegeoip.rb | 17 +++++++++++++++++
 lib/geocoder/request.rb           |  7 +------
 3 files changed, 25 insertions(+), 6 deletions(-)

diff --git a/lib/geocoder/lookups/base.rb b/lib/geocoder/lookups/base.rb
index 8b2ddd11..3d8c66fe 100644
--- a/lib/geocoder/lookups/base.rb
+++ b/lib/geocoder/lookups/base.rb
@@ -88,6 +88,13 @@ module Geocoder
         end
       end
 
+      ##
+      # Is the given string a loopback IP address?
+      #
+      def loopback_address?(ip)
+        !!(ip == "0.0.0.0" or ip.match(/^127/))
+      end
+
       ##
       # Simulate ActiveSupport's Object#to_query.
       #
diff --git a/lib/geocoder/lookups/freegeoip.rb b/lib/geocoder/lookups/freegeoip.rb
index 791bac4c..dcc5e44f 100644
--- a/lib/geocoder/lookups/freegeoip.rb
+++ b/lib/geocoder/lookups/freegeoip.rb
@@ -7,6 +7,8 @@ module Geocoder::Lookup
     private # ---------------------------------------------------------------
 
     def result(query, reverse = false)
+      # don't look up a loopback address, just return the stored result
+      return reserved_result(query) if loopback_address?(query)
       begin
         if doc = fetch_data(query, reverse)
           doc
@@ -16,6 +18,21 @@ module Geocoder::Lookup
       end
     end
 
+    def reserved_result(ip)
+      {
+        "ip"           => ip,
+        "city"         => "",
+        "region_code"  => "",
+        "region_name"  => "",
+        "metrocode"    => "",
+        "zipcode"      => "",
+        "latitude"     => "0",
+        "longitude"    => "0",
+        "country_name" => "Reserved",
+        "country_code" => "RD"
+      }
+    end
+
     def query_url(query, reverse = false)
       "http://freegeoip.net/json/#{query}"
     end
diff --git a/lib/geocoder/request.rb b/lib/geocoder/request.rb
index 909e9b35..dafb8db0 100644
--- a/lib/geocoder/request.rb
+++ b/lib/geocoder/request.rb
@@ -6,12 +6,7 @@ module Geocoder
 
     def location
       unless defined?(@location)
-        if ip.nil? or ip == "0.0.0.0" or ip.match /^127/ # don't look up loopback
-          # but return a Geocoder::Result for consistency
-          @location = Geocoder::Result::Freegeoip.new("ip" => ip)
-        else
-          @location = Geocoder.search(ip)
-        end
+        @location = Geocoder.search(ip)
       end
       @location
     end
-- 
GitLab