auto_location 0.0.1 → 0.0.4
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +36 -0
- data/data/counties.csv +1 -0
- data/lib/auto_location.rb +22 -3
- data/lib/auto_location/string.rb +25 -1
- data/lib/auto_location/version.rb +1 -1
- data/spec/lib/auto_location_spec.rb +39 -0
- metadata +3 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 7e21890a7f28d651b1c1021d50ec103a895acb76
|
4
|
+
data.tar.gz: 37ce8ddf9551f18fd6c3e99f827f66f5b9e332b5
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: c9a1335bcda168bc529c9a9f8051e3ebaea1ce66d275257dbc5902f18f402fd41d1316636747ba8ae712be575fee302be5a8208d2fae7daf4a867e3555185778
|
7
|
+
data.tar.gz: 48ed6d4fb1da74ec01cb474b157dbcefb0b8b982315d8e69423f9fc315651dd293b5539549b0cc50723968712268f868c972c9a3e96661d969ce89401425e3bf
|
data/README.md
CHANGED
@@ -1 +1,37 @@
|
|
1
1
|
# AutoLoc
|
2
|
+
If a string contains a US zipcode/city/state, this gem will convert it into a parsed ruby object including a valid location.
|
3
|
+
|
4
|
+
# Install
|
5
|
+
Add the following into your Rails Gemfile
|
6
|
+
```ruby
|
7
|
+
gem 'auto_location'
|
8
|
+
```
|
9
|
+
Then run bundler to install
|
10
|
+
```ruby
|
11
|
+
$ bundle
|
12
|
+
or
|
13
|
+
$ bundle install
|
14
|
+
```
|
15
|
+
Or install directly on command line
|
16
|
+
```ruby
|
17
|
+
$ gem install auto_location
|
18
|
+
```
|
19
|
+
|
20
|
+
# Usage Example
|
21
|
+
After the gem is installed, in Ruby Code:
|
22
|
+
```ruby
|
23
|
+
'95129'.validated_location => {location: {zipcode: '95129', city: "San Jose", state: "CA"}, type: 'zipcode'}
|
24
|
+
'San Jose, CA'.validated_location => {location: {city: "San Jose", state: "CA"}, type: 'city'}
|
25
|
+
'CA'.validated_location => {location: 'CA', type: 'state'}
|
26
|
+
```
|
27
|
+
The string can also include some unuseful info:
|
28
|
+
```ruby
|
29
|
+
'San Jose, Wait! Where am I???'.validated_location => {location: {city: "San Jose", state: "CA"}, type: 'city'}
|
30
|
+
```
|
31
|
+
If the string is not able to be parsed:
|
32
|
+
```ruby
|
33
|
+
'1428 random text, 35000, San Josa, CC'.validated_location => {error: "Location Not Found"}
|
34
|
+
```
|
35
|
+
|
36
|
+
# Notice
|
37
|
+
The geo location data in the gem doesn't contain all location in US, and some of the parsing logic may not meet your requirement. But! We will make it better!
|
data/data/counties.csv
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
Autauga County,AL
|
data/lib/auto_location.rb
CHANGED
@@ -5,11 +5,12 @@ else
|
|
5
5
|
require 'faster_csv'
|
6
6
|
end
|
7
7
|
|
8
|
-
require 'auto_location/string'
|
8
|
+
require 'auto_location/string.rb'
|
9
9
|
|
10
10
|
module AutoLocation
|
11
11
|
city_file = File.open(File.join(File.dirname(__FILE__), '..', 'data', 'cities.csv'))
|
12
12
|
state_file = File.open(File.join(File.dirname(__FILE__), '..', 'data', 'states.csv'))
|
13
|
+
county_file = File.open(File.join(File.dirname(__FILE__), '..', 'data', 'counties.csv'))
|
13
14
|
|
14
15
|
csv_method = lambda{ |x| RUBY_VERSION.to_f >= 1.9 ? CSV.read(x) : FasterCSV.parse(x) }
|
15
16
|
# regular expressions for city: CITY_NAME_PART1.*PART2.*....*STATE.*
|
@@ -21,8 +22,8 @@ module AutoLocation
|
|
21
22
|
]
|
22
23
|
end
|
23
24
|
@cities_hash ||= Hash[(csv_method.call(city_file)).map do |x|
|
24
|
-
|
25
|
-
|
25
|
+
[(x[2] + ', ' + x[1]).upcase, [x[2], x[1]]]
|
26
|
+
end]
|
26
27
|
@zips ||= Hash[(csv_method.call(city_file)).map do |x|
|
27
28
|
[x[0].to_i, [x[2], x[1]]]
|
28
29
|
end]
|
@@ -31,6 +32,16 @@ module AutoLocation
|
|
31
32
|
x[0] = state.upcase
|
32
33
|
x << state
|
33
34
|
end]
|
35
|
+
@counties ||= csv_method.call(county_file).map do |x|
|
36
|
+
[ Regexp.new(((x[0].split(/[\s\,]/).map(&:strip) << ('(' + x[1] + ')')).join('.*') + '*.*').upcase),
|
37
|
+
x[0],
|
38
|
+
x[1]
|
39
|
+
]
|
40
|
+
end
|
41
|
+
@counties_hash ||= Hash[(csv_method.call(county_file)).map do |x|
|
42
|
+
[(x[0] + ', ' + x[1]).upcase, [x[0], x[1]]]
|
43
|
+
end]
|
44
|
+
|
34
45
|
# default result if zipcode, city, state search all failed
|
35
46
|
@not_found_location ||= {error: "Location Not Found"}.freeze
|
36
47
|
|
@@ -51,6 +62,14 @@ module AutoLocation
|
|
51
62
|
@states
|
52
63
|
end
|
53
64
|
|
65
|
+
def counties
|
66
|
+
@counties
|
67
|
+
end
|
68
|
+
|
69
|
+
def counties_hash
|
70
|
+
@counties_hash
|
71
|
+
end
|
72
|
+
|
54
73
|
def not_found_location
|
55
74
|
@not_found_location
|
56
75
|
end
|
data/lib/auto_location/string.rb
CHANGED
@@ -4,7 +4,7 @@ class String
|
|
4
4
|
# If search includes valid zipcode, return zipcode
|
5
5
|
# If zipcode doesn't exist, do city search.
|
6
6
|
# If city doesn't exist, do state search.
|
7
|
-
zipcode(self) || city_perfect_match(self) ||
|
7
|
+
zipcode(self) || city_perfect_match(self) || county_perfect_match(self) || city_or_county(self) || state(self) || AutoLocation.not_found_location
|
8
8
|
end
|
9
9
|
|
10
10
|
# Check if zipcode exists
|
@@ -22,6 +22,14 @@ class String
|
|
22
22
|
result == nil ? false : { location: {city: result[0], state: result[1]}, type: 'city' }
|
23
23
|
end
|
24
24
|
|
25
|
+
def city_or_county(input)
|
26
|
+
city_res = city(input)
|
27
|
+
county_res = county(input)
|
28
|
+
return county_res if city_res == false
|
29
|
+
return city_res if county_res == false
|
30
|
+
city_res[:location][:city].split(' ').length >= county_res[:location][:county].split(' ').length ? city_res : county_res
|
31
|
+
end
|
32
|
+
|
25
33
|
# Find a city with the search string
|
26
34
|
def city(city)
|
27
35
|
city = city.upcase
|
@@ -43,4 +51,20 @@ class String
|
|
43
51
|
end
|
44
52
|
false
|
45
53
|
end
|
54
|
+
|
55
|
+
def county(county)
|
56
|
+
county = county.upcase
|
57
|
+
results = []
|
58
|
+
AutoLocation.counties.find_all do |row|
|
59
|
+
results << row unless county[row[0]] == nil
|
60
|
+
end
|
61
|
+
result = results == [] ? nil : results.max {|a,b| a[1].length <=> b[1].length}
|
62
|
+
result == nil ? false : { location: {county: result[1], state: result[2]}, type: 'county' }
|
63
|
+
end
|
64
|
+
|
65
|
+
def county_perfect_match(county)
|
66
|
+
county = county.upcase
|
67
|
+
result = AutoLocation.counties_hash[county]
|
68
|
+
result == nil ? false : { location: {county: result[0], state: result[1]}, type: 'county' }
|
69
|
+
end
|
46
70
|
end
|
@@ -21,6 +21,10 @@ describe 'auto location parse location from string' do
|
|
21
21
|
{location: 'California', type: 'state'}
|
22
22
|
end
|
23
23
|
|
24
|
+
let(:valid_county_response) do
|
25
|
+
{ location: {county: 'Orange County', state: 'CA'}, type: 'county' }
|
26
|
+
end
|
27
|
+
|
24
28
|
describe 'get zipcode' do
|
25
29
|
it 'when input contains valid zipcode' do
|
26
30
|
expect('string'.zipcode('hello world, San Jose, CA, 95129')).to eq(valid_zip_code_response)
|
@@ -53,6 +57,23 @@ describe 'auto location parse location from string' do
|
|
53
57
|
end
|
54
58
|
end
|
55
59
|
|
60
|
+
describe 'get county' do
|
61
|
+
it 'when input contains valid county' do
|
62
|
+
expect('string'.county('1428 downtown south, Orange County CA')).to eq(valid_county_response)
|
63
|
+
expect('string'.county('Orange some text County, some textCA')).to eq(valid_county_response)
|
64
|
+
expect('string'.county('orangecountyca')).to eq(valid_county_response)
|
65
|
+
expect('string'.county('some text orange some text county some text')).to eq(valid_county_response)
|
66
|
+
end
|
67
|
+
|
68
|
+
it 'when input does not contain valid county' do
|
69
|
+
expect('string'.county('1428 orancoutttttt')).to be_falsey
|
70
|
+
end
|
71
|
+
|
72
|
+
it 'when input perfectly matches to a county' do
|
73
|
+
expect('string'.county_perfect_match('Orange County, CA')).to eq(valid_county_response)
|
74
|
+
end
|
75
|
+
end
|
76
|
+
|
56
77
|
describe 'get state' do
|
57
78
|
it 'when input contains valid state' do
|
58
79
|
expect('string'.state('ca')).to eq(valid_state_response_short)
|
@@ -69,6 +90,12 @@ describe 'auto location parse location from string' do
|
|
69
90
|
end
|
70
91
|
end
|
71
92
|
|
93
|
+
describe 'get city or county' do
|
94
|
+
it 'when county matches longer than city' do
|
95
|
+
expect('string'.city_or_county('some Orange County, CA')).to eq(valid_county_response)
|
96
|
+
end
|
97
|
+
end
|
98
|
+
|
72
99
|
describe 'get validated location' do
|
73
100
|
it 'when input contains valid zip' do
|
74
101
|
expect('1428 downtown south San Jose, 95129, San Jose, CA'.validated_location).to eq(valid_zip_code_response)
|
@@ -78,6 +105,10 @@ describe 'auto location parse location from string' do
|
|
78
105
|
expect('1428 downtown south San Jose, 35000, San Jose, CA'.validated_location).to eq(valid_city_response)
|
79
106
|
end
|
80
107
|
|
108
|
+
it 'when input contains valid county' do
|
109
|
+
expect('1428 downtown, some text, Orange County, CA'.validated_location).to eq(valid_county_response)
|
110
|
+
end
|
111
|
+
|
81
112
|
it 'when input contains valid state' do
|
82
113
|
expect('1428 random text, 35000, San Josa, CA'.validated_location).to eq(valid_state_response_short)
|
83
114
|
end
|
@@ -85,5 +116,13 @@ describe 'auto location parse location from string' do
|
|
85
116
|
it 'when input contains no valid location' do
|
86
117
|
expect('1428 random text, 35000, San Josa, CC'.validated_location).to eq(not_found_location_response)
|
87
118
|
end
|
119
|
+
|
120
|
+
it 'when input contains pure state' do
|
121
|
+
expect('CA'.validated_location).to eq(valid_state_response_short)
|
122
|
+
end
|
123
|
+
|
124
|
+
it 'county messed up test' do
|
125
|
+
expect('adfsafasfa OrangeCOuntyCA dfsafasfs'.validated_location).to eq(valid_county_response)
|
126
|
+
end
|
88
127
|
end
|
89
128
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: auto_location
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.4
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Lu Zou
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2016-09-
|
11
|
+
date: 2016-09-07 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: fastercsv
|
@@ -68,6 +68,7 @@ files:
|
|
68
68
|
- Rakefile
|
69
69
|
- auto_location.gemspec
|
70
70
|
- data/cities.csv
|
71
|
+
- data/counties.csv
|
71
72
|
- data/states.csv
|
72
73
|
- data/zips.csv
|
73
74
|
- lib/auto_location.rb
|