Skip to content

Instantly share code, notes, and snippets.

@virolea
Created April 28, 2016 16:21
Show Gist options
  • Save virolea/b0cfcb326f48f5749466dc1eab0dcafe to your computer and use it in GitHub Desktop.
Save virolea/b0cfcb326f48f5749466dc1eab0dcafe to your computer and use it in GitHub Desktop.
Invite people from 100km of headquarters - from text file
class Customer
include Math
EARTH_RADIUS = 6371 # Earth Radius in km
attr_accessor :id, :name, :latitude, :longitude
def initialize(params)
@id = params["user_id"]
@name = params["name"]
@latitude = params["latitude"].to_f
@longitude = params["longitude"].to_f
end
# Compute distance, by-default setted to Intercom Dublin Offices
def compute_distance(latitude = 53.3381985, longitude = -6.2592576)
delta_lambda = to_rad((@longitude - longitude).abs)
delta_sigma = acos(sin(to_rad(@latitude)) * sin(to_rad(latitude)) + cos(to_rad(@latitude)) * cos(to_rad(latitude)) * cos(delta_lambda))
EARTH_RADIUS * delta_sigma
end
private
def to_rad(coord)
coord * Math::PI / 180
end
end
require 'customer'
RSpec.describe Customer do
before(:all) do
customer_params = { "user_id" => 1, "name" => "Vincent Rolea", "latitude" => 48.648118, "longitude" => 2.453116}
@customer = Customer.new(customer_params)
end
describe "#new" do
it "takes four parameters an returns a Customer Object" do
expect(@customer).to be_an_instance_of(Customer)
end
it "returns the correct id" do
expect(@customer.id).to eq(1)
end
it "returns the correct name" do
expect(@customer.name).to eq("Vincent Rolea")
end
it "returns the correct latitude" do
expect(@customer.latitude).to eq(48.648118)
end
it "returns the correct longitude" do
expect(@customer.longitude).to eq(2.453116)
end
end
describe "#compute_distance" do
it "correctly computes distance from Intercom Dublin by default" do
expect(@customer.compute_distance.round).to eq(801)
end
it "correctly computes distance from anywhere" do
expect(@customer.compute_distance(37.788807, -122.400319).round).to eq(8974)
end
end
end
{"latitude": "53.2451022", "user_id": 4, "name": "Ian Kehoe", "longitude": "-6.238335"}
{"latitude": "51.8856167", "user_id": 2, "name": "Ian McArdle", "longitude": "-10.4240951"}
{"latitude": "53.1302756", "user_id": 5, "name": "Nora Dempsey", "longitude": "-6.2397222"}
{"latitude": "52.3191841", "user_id": 3, "name": "Jack Enright", "longitude": "-8.5072391"}
{"latitude": "53.1229599", "user_id": 6, "name": "Theresa Enright", "longitude": "-6.2705202"}
{"latitude": "51.92893", "user_id": 1, "name": "Alice Cahill", "longitude": "-10.27699"}
{"latitude": "52.986375", "user_id": 12, "name": "Christina McArdle", "longitude": "-6.043701"}
{"latitude": "51.92893", "user_id": 1, "name": "Alice Cahill", "longitude": "-10.27699"}
{"latitude": "51.8856167", "user_id": 2, "name": "Ian McArdle", "longitude": "-10.4240951"}
{"latitude": "52.3191841", "user_id": 3, "name": "Jack Enright", "longitude": "-8.5072391"}
{"latitude": "53.807778", "user_id": 28, "name": "Charlie Halligan", "longitude": "-7.714444"}
{"latitude": "53.4692815", "user_id": 7, "name": "Frank Kehoe", "longitude": "-9.436036"}
{"latitude": "54.0894797", "user_id": 8, "name": "Eoin Ahearn", "longitude": "-6.18671"}
{"latitude": "53.038056", "user_id": 26, "name": "Stephen McArdle", "longitude": "-7.653889"}
{"latitude": "54.1225", "user_id": 27, "name": "Enid Gallagher", "longitude": "-8.143333"}
{"latitude": "53.1229599", "user_id": 6, "name": "Theresa Enright", "longitude": "-6.2705202"}
{"latitude": "52.2559432", "user_id": 9, "name": "Jack Dempsey", "longitude": "-7.1048927"}
{"latitude": "52.240382", "user_id": 10, "name": "Georgina Gallagher", "longitude": "-6.972413"}
{"latitude": "53.2451022", "user_id": 4, "name": "Ian Kehoe", "longitude": "-6.238335"}
{"latitude": "53.1302756", "user_id": 5, "name": "Nora Dempsey", "longitude": "-6.2397222"}
{"latitude": "53.008769", "user_id": 11, "name": "Richard Finnegan", "longitude": "-6.1056711"}
{"latitude": "53.1489345", "user_id": 31, "name": "Alan Behan", "longitude": "-6.8422408"}
{"latitude": "53", "user_id": 13, "name": "Olive Ahearn", "longitude": "-7"}
{"latitude": "51.999447", "user_id": 14, "name": "Helen Cahill", "longitude": "-9.742744"}
{"latitude": "52.966", "user_id": 15, "name": "Michael Ahearn", "longitude": "-6.463"}
{"latitude": "52.366037", "user_id": 16, "name": "Ian Larkin", "longitude": "-8.179118"}
{"latitude": "54.180238", "user_id": 17, "name": "Patricia Cahill", "longitude": "-5.920898"}
{"latitude": "53.0033946", "user_id": 39, "name": "Lisa Ahearn", "longitude": "-6.3877505"}
{"latitude": "52.228056", "user_id": 18, "name": "Bob Larkin", "longitude": "-7.915833"}
{"latitude": "54.133333", "user_id": 24, "name": "Rose Enright", "longitude": "-6.433333"}
{"latitude": "55.033", "user_id": 19, "name": "Enid Cahill", "longitude": "-8.112"}
{"latitude": "53.521111", "user_id": 20, "name": "Enid Enright", "longitude": "-9.831111"}
{"latitude": "51.802", "user_id": 21, "name": "David Ahearn", "longitude": "-9.442"}
{"latitude": "54.374208", "user_id": 22, "name": "Charlie McArdle", "longitude": "-8.371639"}
{"latitude": "53.74452", "user_id": 29, "name": "Oliver Ahearn", "longitude": "-7.11167"}
{"latitude": "53.761389", "user_id": 30, "name": "Nick Enright", "longitude": "-7.2875"}
{"latitude": "54.080556", "user_id": 23, "name": "Eoin Gallagher", "longitude": "-6.361944"}
{"latitude": "52.833502", "user_id": 25, "name": "David Behan", "longitude": "-8.522366"}
require_relative 'lib/parser'
parser = Parser.new
parser.print_customers
require_relative 'customer'
require 'json'
class Parser
def initialize(filepath=File.expand_path("lib/customers.txt"))
@filepath = filepath
end
def select_customers()
filtered_customers = []
customers = parse_customers
customers.each do |customer|
filtered_customers << customer unless customer.compute_distance > 100
end
filtered_customers
end
def parse_customers
customers = []
File.foreach(@filepath) do |row|
customers << Customer.new(JSON.parse(row))
end
customers.sort_by { |customer| customer.id }
end
def print_customers
customers = select_customers
customers.each do |customer|
puts "#{customer.id}. #{customer.name}"
end
end
end
require 'parser'
RSpec.describe Parser do
before(:all) do
@parser = Parser.new(File.expand_path("spec/customers_spec.txt"))
@parser.print_customers
end
context "data import" do
describe "#parse_customers" do
it "must import correctly all customers present in the text file" do
expect(@parser.parse_customers.length).to eq(6)
end
end
it "reads the text file and parse customers" do
customer = @parser.parse_customers.first
expect(customer.id).to eq(1)
expect(customer.name).to eq("Alice Cahill")
expect(customer.latitude).to eq(51.92893)
expect(customer.longitude).to eq(-10.27699)
end
end
context "data treatment" do
describe "#select_customers" do
it "selects the correct number of customers within 100km" do
customers = @parser.select_customers
expect(customers.length).to eq(3)
end
it "print correct names with ascendant ids" do
expect(STDOUT).to receive(:puts).with("4. Ian Kehoe").ordered
expect(STDOUT).to receive(:puts).with("5. Nora Dempsey").ordered
expect(STDOUT).to receive(:puts).with("6. Theresa Enright").ordered
@parser.print_customers
end
end
end
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment