Geocoder
This article, Geocoder is a gem that allows you to create geo-aware applications by providing a powerful abstraction layer for geocoding manipulations.
Table of contents
How to install Geocoder
Reminder:
Make sure that your containers are up and running.
In your Gemfile, add gem geocoder.
gem 'geocoder'
Then run bundle install.
root@0122:/usr/src/app# bundle install
...
Installing geocoder 1.8.1
Bundle complete! 31 Gemfile dependencies, 118 gems now installed.
Use `bundle info [gemname]` to see where a bundled gem is installed.
Usage
Before we use the geocoder, let’s add an ip address column with string type in our posts table. In your terminal run rails g migration add_ip_address_in_posts.
root@a65be41abcb4:/usr/src/app# rails g migration add_ip_address_in_posts
invoke active_record
create db/migrate/xxxxxxxxxxxxxx_add_ip_address_in_posts.rb
# db/migrate/xxxxxxxxxxxxxx_add_ip_address_in_posts
class AddIpAddressInPosts < ActiveRecord::Migration[7.0]
def change
add_column :posts, :ip_address, :string
end
end
Then migrate run rails db:migrate.
root@a65be41abcb4:/usr/src/app# rails db:migrate
== XXXXXXXXXXXXXX AddIpAddressInPosts: migrating ==============================
-- add_column(:posts, :ip_address, :string)
-> 0.0542s
== XXXXXXXXXXXXXX AddIpAddressInPosts: migrated (0.0543s) =====================
On your posts_controller.rb under the app/controllers add the following codes.
# app/controllers/posts_controller.rb
# ...
def create
@post = Post.new(post_params)
@post.user = current_user
+ if Rails.env.development?
+ @post.ip_address = Net::HTTP.get(URI.parse('http://checkip.amazonaws.com/')).squish
+ else
+ @post.ip_address = request.remote_ip
+ end
# ...
end
# ...
if the project is in development, we will be using the Net::HTTP.get(URI.parse('http://checkip.amazonaws.com/')).squish to return the IP address thru amazonaws.
If the project is not in development we will be using the request.remote_ip. The remote.ip_address is the public IP address of your network.
Create post to see the result of your ip address. After creating a post go to your terminal and run rails c.
root@a65be41abcb4:/usr/src/app# rails c
Loading development environment (Rails 7.0.4)
irb(main):001:0>
In your console, run @ip_address = Post.last.ip_address.
irb(main):001:0> @location = Post.last.ip_address
Post Load (0.6ms) SELECT `posts`.* FROM `posts` WHERE `posts`.`deleted_at` IS NULL ORDER BY `posts`.`id` DESC LIMIT 1
=> "xxx.xx.xxx.xxx"
The return value is the IP address of the last post.
The @location will be using argument below in Geocoder.search. It is hard to read/know what location of the post so by using Geocoder it helps to read/know what location of the post.
How to use Geocoder
The basic functionality will run an @location through Geocoder and return the location’s latitude and longitude. To run a basic geocoder search, in your console run this command:
irb(main):002:0> Geocoder.search(@location).first.coordinates
=> [xx.xxxx, xxx.xxxx]
The return value is an array of latitude and longitude.
irb(main):003:0> Geocoder.search(@location).first.city # Return location city
irb(main):004:0> Geocoder.search(@location).first.region # Return location region
irb(main):005:0> Geocoder.search(@location).first.country # Return location country
You can try other examples depending on what you need to display.
Open the index.html.erb and add the geocoder to identify what location of every post under the app/views.
<!-- app/views/posts/index.html.erb -->
<!-- ... -->
<td>moods</td>
+ <td>location</td>
<td>created_at</td>
<!-- ... -->
<!-- ... -->
<td><%= post.moods.pluck(:name).join(', ') %></td>
+ <td><%= Geocoder.search(post.ip_address).first&.country %></td>
<td><%= post.created_at %></td>
<!-- ... -->
The return value is location’s country. Reload your post index page for the result.
Now we successfully integrated Geocoder in our application. To know more about Geocoder, you can read Geocoder.