simple_geolocation 0.0.1

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.
data/.gitignore ADDED
@@ -0,0 +1,7 @@
1
+ *.gem
2
+ .bundle
3
+ Gemfile.lock
4
+ pkg/*
5
+ *.swp
6
+ *.swo
7
+ *.DS_Store
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source "http://rubygems.org"
2
+
3
+ # Specify your gem's dependencies in simple_geolocation.gemspec
4
+ gemspec
data/Rakefile ADDED
@@ -0,0 +1,2 @@
1
+ require 'bundler'
2
+ Bundler::GemHelper.install_tasks
@@ -0,0 +1,7 @@
1
+ require 'active_support/core_ext'
2
+ require File.join(File.dirname(__FILE__), 'simple_geolocation/utils/remove_accents')
3
+ module SimpleGeolocation
4
+ autoload :Geocoder , 'simple_geolocation/geocoder'
5
+ autoload :Location , 'simple_geolocation/location'
6
+ autoload :Geoworkers , 'simple_geolocation/geoworkers/geoworkers'
7
+ end
@@ -0,0 +1,39 @@
1
+ module SimpleGeolocation
2
+ class Geocoder
3
+
4
+ attr_reader :success, :raw_location, :location
5
+ alias :success? :success
6
+
7
+ delegate *(Location::ATTRIBUTES + [:completeness]), :to => :location
8
+
9
+ def initialize(raw_location)
10
+ @raw_location = raw_location
11
+ end
12
+
13
+ def ip?
14
+ !!/^(\d+\.){3}\d+$/.match(@raw_location)
15
+ end
16
+
17
+ # Only brazilian zipcode is supported.
18
+ def zip?
19
+ return false if ip?
20
+ number = @raw_location.to_s.gsub(/(\.|\D|\-|\s)/, '')
21
+ number.size == 8
22
+ end
23
+
24
+ def address?
25
+ !ip? && !zip?
26
+ end
27
+
28
+ def geocode!
29
+ @geoworker = Geoworkers::Base.instantiate_geoworker_based_on(self)
30
+ @geoworker.process!
31
+ @location = @geoworker.location
32
+ end
33
+
34
+ def success!
35
+ @success = true
36
+ end
37
+
38
+ end
39
+ end
@@ -0,0 +1,27 @@
1
+ module SimpleGeolocation
2
+ module Geoworkers
3
+ class Base
4
+
5
+ attr_reader :location, :geocoder, :success
6
+ alias :success? :success
7
+
8
+ def initialize(geocoder)
9
+ @geocoder = geocoder
10
+ end
11
+
12
+ def process!
13
+ raise NotImplementedError
14
+ end
15
+
16
+ def self.instantiate_geoworker_based_on(geocoder)
17
+ if geocoder.ip?
18
+ GeoIP.new(geocoder)
19
+ elsif geocoder.zip?
20
+ Geozip.new(geocoder)
21
+ else
22
+ Geokit.new(geocoder)
23
+ end
24
+ end
25
+ end
26
+ end
27
+ end
@@ -0,0 +1,34 @@
1
+ require 'geoip'
2
+ module SimpleGeolocation
3
+ module Geoworkers
4
+ class GeoIP < Base
5
+
6
+ def process!
7
+ get_location!
8
+ geocoder.success! if success?
9
+ end
10
+
11
+ private
12
+
13
+ def ip_geocoder
14
+ @ip_geocoder ||= ::GeoIP.new(File.join(File.dirname(__FILE__), 'data', 'GeoLiteCity.dat'))
15
+ end
16
+
17
+ def get_location!
18
+ result = ip_geocoder.city(geocoder.raw_location)
19
+ if @success = result && result.city_name.present? && result.region_name.present?
20
+ @location = Location.new(
21
+ :lat => result.latitude,
22
+ :lng => result.longitude,
23
+ :city => result.city_name,
24
+ :state => result.region_name,
25
+ :provider => "geoip"
26
+ )
27
+ else
28
+ Geokit.new(geocoder).process!
29
+ end
30
+ end
31
+
32
+ end
33
+ end
34
+ end
@@ -0,0 +1,36 @@
1
+ require 'geokit'
2
+ module SimpleGeolocation
3
+ module Geoworkers
4
+ class Geokit < Base
5
+
6
+ def process!
7
+ get_location!
8
+ geocoder.success! if success?
9
+ end
10
+
11
+ private
12
+
13
+ def multi_geocoder
14
+ @multi_geocoder ||= ::Geokit::Geocoders::MultiGeocoder
15
+ end
16
+
17
+ def get_location!
18
+ result = multi_geocoder.geocode(geocoder.raw_location.removeaccents)
19
+ if @success = result.success
20
+ @location = Location.new(
21
+ :lat => result.lat,
22
+ :lng => result.lng,
23
+ :city => result.city,
24
+ :state => result.state,
25
+ :street => result.street_name,
26
+ :number => result.street_number,
27
+ :zip => result.zip,
28
+ :district => result.district,
29
+ :provider => result.provider
30
+ )
31
+ end
32
+ end
33
+
34
+ end
35
+ end
36
+ end
@@ -0,0 +1,8 @@
1
+ module SimpleGeolocation
2
+ module Geoworkers
3
+ autoload :Base, 'simple_geolocation/geoworkers/base'
4
+ autoload :GeoIP, 'simple_geolocation/geoworkers/geoip/geoip'
5
+ autoload :Geokit, 'simple_geolocation/geoworkers/geokit/geokit'
6
+ autoload :Geozip, 'simple_geolocation/geoworkers/geozip/geozip'
7
+ end
8
+ end
@@ -0,0 +1,32 @@
1
+ require 'brcep'
2
+ module SimpleGeolocation
3
+ module Geoworkers
4
+ class Geozip < Base
5
+
6
+ def process!
7
+ get_location!
8
+ geocoder.success! if success?
9
+ end
10
+
11
+ private
12
+
13
+ def get_location!
14
+ begin
15
+ result = ::BuscaEndereco.por_cep(geocoder.raw_location)
16
+ if @success = result && result.present?
17
+ street = "#{result.first} #{result.second}"
18
+ other_location_data = result[2..-1].join(', ')
19
+ new_raw_location = "#{street}, #{other_location_data}"
20
+ geokit = Geokit.new(Geocoder.new(new_raw_location))
21
+ geokit.process!
22
+ @success = geokit.success?
23
+ @location = geokit.location
24
+ end
25
+ rescue
26
+ @success = false
27
+ end
28
+ end
29
+
30
+ end
31
+ end
32
+ end
@@ -0,0 +1,23 @@
1
+ module SimpleGeolocation
2
+ class Location
3
+ ATTRIBUTES = [:lat, :lng, :city, :state, :provider, :zip, :street, :district, :number]
4
+ attr_accessor *ATTRIBUTES
5
+
6
+ def initialize(attributes = {})
7
+ unknown_attributes = attributes.keys.reject { |k| ATTRIBUTES.include?(k) }
8
+ raise ArgumentError, "Unknown parameters: #{unknown_attributes.join(', ')}" unless unknown_attributes.empty?
9
+ attributes.each do |k, v|
10
+ send("#{k}=", v)
11
+ end
12
+ end
13
+
14
+ def completeness(attributes = ATTRIBUTES)
15
+ total = attributes.size
16
+ used = attributes.reject {|attr| send(attr).blank? }.size
17
+ return 100 if used >= total
18
+ (used.to_f / total.to_f * 100.0).to_i
19
+ end
20
+
21
+ end
22
+ end
23
+
@@ -0,0 +1,61 @@
1
+ class String
2
+ # The extended characters map used by removeaccents. The accented characters
3
+ # are coded here using their numerical equivalent to sidestep encoding issues.
4
+ # These correspond to ISO-8859-1 encoding.
5
+ ACCENTS_MAPPING = {
6
+ 'E' => [200,201,202,203],
7
+ 'e' => [232,233,234,235],
8
+ 'A' => [192,193,194,195,196,197],
9
+ 'a' => [224,225,226,227,228,229,230],
10
+ 'C' => [199],
11
+ 'c' => [231],
12
+ 'O' => [210,211,212,213,214,216],
13
+ 'o' => [242,243,244,245,246,248],
14
+ 'I' => [204,205,206,207],
15
+ 'i' => [236,237,238,239],
16
+ 'U' => [217,218,219,220],
17
+ 'u' => [249,250,251,252],
18
+ 'N' => [209],
19
+ 'n' => [241],
20
+ 'Y' => [221],
21
+ 'y' => [253,255],
22
+ 'AE' => [306],
23
+ 'ae' => [346],
24
+ 'OE' => [188],
25
+ 'oe' => [189]
26
+ }
27
+
28
+
29
+ # Remove the accents from the string. Uses String::ACCENTS_MAPPING as the source map.
30
+ def removeaccents
31
+ str = String.new(self)
32
+ String::ACCENTS_MAPPING.each {|letter,accents|
33
+ packed = accents.pack('U*')
34
+ rxp = Regexp.new("[#{packed}]", nil)
35
+ str.gsub!(rxp, letter)
36
+ }
37
+
38
+ str
39
+ end
40
+
41
+
42
+ # Convert a string to a format suitable for a URL without ever using escaped characters.
43
+ # It calls strip, removeaccents, downcase (optional) then removes the spaces (optional)
44
+ # and finally removes any characters matching the default regexp (/[^-_A-Za-z0-9]/).
45
+ #
46
+ # Options
47
+ #
48
+ # * :downcase => call downcase on the string (defaults to true)
49
+ # * :convert_spaces => Convert space to underscore (defaults to false)
50
+ # * :regexp => The regexp matching characters that will be converting to an empty string (defaults to /[^-_A-Za-z0-9]/)
51
+ def urlize(options = {})
52
+ options[:downcase] ||= true
53
+ options[:convert_spaces] ||= false
54
+ options[:regexp] ||= /[^-_A-Za-z0-9]/
55
+
56
+ str = self.strip.removeaccents
57
+ str.downcase! if options[:downcase]
58
+ str.gsub!(/\ /,'_') if options[:convert_spaces]
59
+ str.gsub(options[:regexp], '')
60
+ end
61
+ end
@@ -0,0 +1,3 @@
1
+ module SimpleGeolocation
2
+ VERSION = "0.0.1"
3
+ end
@@ -0,0 +1,31 @@
1
+ # -*- encoding: utf-8 -*-
2
+ $:.push File.expand_path("../lib", __FILE__)
3
+ require "simple_geolocation/version"
4
+
5
+ Gem::Specification.new do |s|
6
+ s.name = "simple_geolocation"
7
+ s.version = SimpleGeolocation::VERSION
8
+ s.platform = Gem::Platform::RUBY
9
+ s.authors = ["Esdras Mayrink"]
10
+ s.email = ["falecom@oesdras.com.br"]
11
+ s.homepage = "http://oesdras.com.br"
12
+ s.summary = %q{A gem that fetch locations based on IP, ZIP and ordinary address through several existing geolocation gems.}
13
+ s.description = %q{
14
+ This gem is used with geolocation in mind, meaning that the main goal is to get a latitude and longitude, but it will return additional data if
15
+ available. With this gem you can pass an IP number or an ZIP number or an ordinary address and it will try to get as many information as possible
16
+ about the given argument.
17
+ }
18
+
19
+ s.add_development_dependency "rspec"
20
+ s.add_dependency "geokit"
21
+ s.add_dependency "geoip"
22
+ s.add_dependency "activesupport"
23
+ s.add_dependency "brcep"
24
+
25
+ s.rubyforge_project = "simple_geolocation"
26
+
27
+ s.files = `git ls-files`.split("\n")
28
+ s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
29
+ s.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
30
+ s.require_paths = ["lib"]
31
+ end
@@ -0,0 +1,63 @@
1
+ # coding: utf-8
2
+ require File.join(File.dirname(__FILE__), '..', 'lib', 'simple_geolocation')
3
+
4
+ describe SimpleGeolocation do
5
+
6
+
7
+ it 'should identify if the given location is an ip' do
8
+ @geo = SimpleGeolocation::Geocoder.new("74.125.113.105")
9
+ @geo.ip?.should be_true
10
+ @geo.zip?.should be_false
11
+ @geo.address?.should be_false
12
+ end
13
+
14
+ it 'should identify if the given location is a zip' do
15
+ @geo = SimpleGeolocation::Geocoder.new("89237-440")
16
+ @geo.ip?.should be_false
17
+ @geo.zip?.should be_true
18
+ @geo.address?.should be_false
19
+ end
20
+
21
+ it 'should identify if the given location is an address' do
22
+ @geo = SimpleGeolocation::Geocoder.new("Joinville - SC")
23
+ @geo.ip?.should be_false
24
+ @geo.address?.should be_true
25
+ @geo.zip?.should be_false
26
+ end
27
+
28
+ it "should return the location of an user's based on IP" do
29
+ @geo = SimpleGeolocation::Geocoder.new("74.125.113.105")
30
+ @geo.ip?.should be_true
31
+ @geo.geocode!
32
+ @geo.success?.should be_true
33
+ @geo.lat.should == 37.41919999999999
34
+ @geo.lng.should == -122.0574
35
+ @geo.completeness.should == 55
36
+ end
37
+
38
+ it "should return the location of an ordinary address" do
39
+ @geo = SimpleGeolocation::Geocoder.new("Rua do Principe, 199, Joinville, SC")
40
+ @geo.address?.should be_true
41
+ @geo.geocode!
42
+ @geo.success?.should be_true
43
+ @geo.lat.should == -26.30101
44
+ @geo.lng.should == -48.8452974
45
+ @geo.completeness.should == 88
46
+ end
47
+
48
+ it "should return the location of a brazilian zipcode (CEP)" do
49
+ @geo = SimpleGeolocation::Geocoder.new("22640100")
50
+ @geo.zip?.should be_true
51
+ @geo.geocode!
52
+ @geo.success?.should be_true
53
+ @geo.street.should == "Av. Das Américas"
54
+ @geo.district.should == "Barra da Tijuca"
55
+ @geo.state.should == "RJ"
56
+ @geo.city.should == "Rio De Janeiro"
57
+ @geo.zip.should == "22640-100"
58
+ @geo.lat.should == -23.0032808
59
+ @geo.lng.should == -43.3230295
60
+ @geo.completeness.should == 88
61
+ end
62
+
63
+ end
metadata ADDED
@@ -0,0 +1,126 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: simple_geolocation
3
+ version: !ruby/object:Gem::Version
4
+ prerelease:
5
+ version: 0.0.1
6
+ platform: ruby
7
+ authors:
8
+ - Esdras Mayrink
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+
13
+ date: 2011-04-04 00:00:00 -03:00
14
+ default_executable:
15
+ dependencies:
16
+ - !ruby/object:Gem::Dependency
17
+ name: rspec
18
+ prerelease: false
19
+ requirement: &id001 !ruby/object:Gem::Requirement
20
+ none: false
21
+ requirements:
22
+ - - ">="
23
+ - !ruby/object:Gem::Version
24
+ version: "0"
25
+ type: :development
26
+ version_requirements: *id001
27
+ - !ruby/object:Gem::Dependency
28
+ name: geokit
29
+ prerelease: false
30
+ requirement: &id002 !ruby/object:Gem::Requirement
31
+ none: false
32
+ requirements:
33
+ - - ">="
34
+ - !ruby/object:Gem::Version
35
+ version: "0"
36
+ type: :runtime
37
+ version_requirements: *id002
38
+ - !ruby/object:Gem::Dependency
39
+ name: geoip
40
+ prerelease: false
41
+ requirement: &id003 !ruby/object:Gem::Requirement
42
+ none: false
43
+ requirements:
44
+ - - ">="
45
+ - !ruby/object:Gem::Version
46
+ version: "0"
47
+ type: :runtime
48
+ version_requirements: *id003
49
+ - !ruby/object:Gem::Dependency
50
+ name: activesupport
51
+ prerelease: false
52
+ requirement: &id004 !ruby/object:Gem::Requirement
53
+ none: false
54
+ requirements:
55
+ - - ">="
56
+ - !ruby/object:Gem::Version
57
+ version: "0"
58
+ type: :runtime
59
+ version_requirements: *id004
60
+ - !ruby/object:Gem::Dependency
61
+ name: brcep
62
+ prerelease: false
63
+ requirement: &id005 !ruby/object:Gem::Requirement
64
+ none: false
65
+ requirements:
66
+ - - ">="
67
+ - !ruby/object:Gem::Version
68
+ version: "0"
69
+ type: :runtime
70
+ version_requirements: *id005
71
+ description: "\n This gem is used with geolocation in mind, meaning that the main goal is to get a latitude and longitude, but it will return additional data if\n available. With this gem you can pass an IP number or an ZIP number or an ordinary address and it will try to get as many information as possible\n about the given argument.\n "
72
+ email:
73
+ - falecom@oesdras.com.br
74
+ executables: []
75
+
76
+ extensions: []
77
+
78
+ extra_rdoc_files: []
79
+
80
+ files:
81
+ - .gitignore
82
+ - Gemfile
83
+ - Rakefile
84
+ - lib/simple_geolocation.rb
85
+ - lib/simple_geolocation/geocoder.rb
86
+ - lib/simple_geolocation/geoworkers/base.rb
87
+ - lib/simple_geolocation/geoworkers/geoip/data/GeoLiteCity.dat
88
+ - lib/simple_geolocation/geoworkers/geoip/geoip.rb
89
+ - lib/simple_geolocation/geoworkers/geokit/geokit.rb
90
+ - lib/simple_geolocation/geoworkers/geoworkers.rb
91
+ - lib/simple_geolocation/geoworkers/geozip/geozip.rb
92
+ - lib/simple_geolocation/location.rb
93
+ - lib/simple_geolocation/utils/remove_accents.rb
94
+ - lib/simple_geolocation/version.rb
95
+ - simple_geolocation.gemspec
96
+ - spec/simple_geolocation_spec.rb
97
+ has_rdoc: true
98
+ homepage: http://oesdras.com.br
99
+ licenses: []
100
+
101
+ post_install_message:
102
+ rdoc_options: []
103
+
104
+ require_paths:
105
+ - lib
106
+ required_ruby_version: !ruby/object:Gem::Requirement
107
+ none: false
108
+ requirements:
109
+ - - ">="
110
+ - !ruby/object:Gem::Version
111
+ version: "0"
112
+ required_rubygems_version: !ruby/object:Gem::Requirement
113
+ none: false
114
+ requirements:
115
+ - - ">="
116
+ - !ruby/object:Gem::Version
117
+ version: "0"
118
+ requirements: []
119
+
120
+ rubyforge_project: simple_geolocation
121
+ rubygems_version: 1.5.2
122
+ signing_key:
123
+ specification_version: 3
124
+ summary: A gem that fetch locations based on IP, ZIP and ordinary address through several existing geolocation gems.
125
+ test_files:
126
+ - spec/simple_geolocation_spec.rb