class DatxRuby::City
Public Class Methods
datax_path=(path)
click to toggle source
# File lib/datx_ruby/city.rb, line 13 def self.datax_path=(path) $datx_path ||= path end
new()
click to toggle source
# File lib/datx_ruby/city.rb, line 8 def initialize @data = IO.binread(datx) @index_size = Util.bytes2long(@data[0], @data[1], @data[2], @data[3]) end
Public Instance Methods
find(ip)
click to toggle source
# File lib/datx_ruby/city.rb, line 17 def find(ip) raise "Invalid IP address" unless ::IPAddr.new(ip).ipv4? low = 0 high = (index_size - 262144 - 262148) / 9 - 1 val = Util.ip2long(ip) while low <= high do mid = (low + high) / 2 pos = mid * 9 + 262148 starts = 0 mid_new = mid - 1 if mid > 0 pos_new = mid_new * 9 + 262148 starts = Util.bytes2long(@data[pos_new], @data[pos_new + 1], @data[pos_new + 2], @data[pos_new + 3]) starts += 1 end ends = Util.bytes2long(@data[pos], @data[pos + 1], @data[pos + 2], @data[pos + 3]) if val < starts high = mid_new elsif val > ends low = mid + 1 else empty = [0].pack('C*') off = Util.bytes2long(empty, @data[pos + 6], @data[pos + 5], @data[pos + 4]) length = Util.bytes2long(empty, empty, @data[pos + 7], @data[pos + 8]) pos = off - 262144 + index_size tmp = @data[pos...pos + length].force_encoding('utf-8') return tmp.split("\t") end end end