Skip to content

Instantly share code, notes, and snippets.

@dansimpson
Last active December 19, 2015 12:19
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save dansimpson/5953938 to your computer and use it in GitHub Desktop.
Save dansimpson/5953938 to your computer and use it in GitHub Desktop.
Small command line utility for fetching GPS coordinates of you iPhone, iPad, or iPod.
#!/usr/bin/env ruby
require "optparse"
require "json"
require "findi"
def report device, mode=:text
name = device.name
# special case for an untracked device
unless device.location_finished?
puts name
puts "-" * name.length
puts "The device is currently being located. Try again shortly."
return
end
hash = {
id: device.id,
name: device.name,
make: device.kind,
model: device.model,
location: {
time: device.location_timestamp,
type: device.location_type,
accuracy: device.horizontal_accuracy,
latitude: device.latitude,
longitude: device.longitude
},
battery: {
status: device.battery_status,
level: device.battery_level
}
}
case mode
when :json
puts hash.to_json
when :csv
puts [
"\"#{device.name}\"",
device.location_timestamp.strftime("%Y-%m-%d %H:%M:%S"),
device.latitude,
device.longitude
].join(",")
when :gmap
puts "http://maps.google.com/?q=#{device.latitude},#{device.longitude}"
else
puts device.name
puts "-" * device.name.length
puts "Latitude: #{device.latitude}"
puts "Longitude: #{device.longitude}"
puts "Time: #{device.location_timestamp.strftime("%Y-%m-%d %H:%M:%S")}"
end
end
options = {}
OptionParser.new { |opts|
opts.banner = "Usage: trackphone [options]"
opts.on("-u", "--user [username]", "Username") do |user|
options[:user] = user
end
opts.on("-p", "--password [password]", "Password") do |password|
options[:password] = password
end
opts.on("-q", "--query [name query]", "Query name of device") do |query|
options[:query] = query
end
opts.on("-m", "--mode [mode]", "Report mode, options: text, json, csv") do |mode|
options[:mode] = mode.to_sym
end
}.parse!
unless options.key?(:user) && options.key?(:password)
puts "Missing user/password option(s)"
exit 1
end
# Fetch devices and settings
devices = Findi::Client.new(options[:user], options[:password]).devices
if options.key?(:query)
devices = devices.select { |d| d.name =~ /#{options[:query]}/i }
end
if devices.nil? || devices.empty?
puts "No devices to track..."
exit 0
end
devices.each { |device|
report device, options[:mode]
}

Install

First, install the findi gem.

$ gem install findi

Put the file in your PATH and chmod +x it.

$ chmod +x ~/.bin/ifind

Run

$ ifind -u 'myemail@mac.com' -p 'mypassword'

Output JSON:

$ ifind -u 'myemail@mac.com' -p 'mypassword' --mode json

Output a Google Maps link:

$ ifind -u 'myemail@mac.com' -p 'mypassword' --mode gmap

Output CSV:

$ ifind -u 'myemail@mac.com' -p 'mypassword' --mode csv
@rickdeboer1987
Copy link

Hello Dan,

Thank you for the excellent work.
However when I try to compile the Ruby script I get the following errors :

iPhone:/var/www root# gem install findi

dyld: lazy symbol binding failed: Symbol not found: __OSSwapInt16
Referenced from: /usr/lib/ruby/1.9.1/arm-darwin9/socket.bundle
Expected in: flat namespace

dyld: Symbol not found: __OSSwapInt16
Referenced from: /usr/lib/ruby/1.9.1/arm-darwin9/socket.bundle
Expected in: flat namespace

Trace/BPT trap: 5

Any idea how to solve this ?

Thanks.
Best regards..

@dansimpson
Copy link
Author

@rickdeboer1987 I didn't see your comment until now. I didn't actually create the findi gem. Which platform are you trying to install on?

@claytonasmith
Copy link

@dansimpson - This is perfect! Thanks a bunch. Worked fine for me on Mac and Linux.

@rickdeboer1987 - findi requires Ruby version >= 1.9.2.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment