#!/usr/bin/ruby
=begin
Purpose:
Updates GeoIP Country (paid) database from MaxMind.com. Requires
valid license key to work.
Why:
1) I hate the idea of running some weird C code ("geoipupdate")
from cron, that's why.
2) I don't want to run "geoipupdate" on all machines using this DB.
Author: Wejn <wejn at box dot cz>
License: GPLv2 (without the "latter" option)
Requires: Ruby >= 1.8, geoip country license (to be of any value)
TS: 20060626181500
=end
# your license key here
$license_key = 'You-wish :-)'
# destination file
$outfile = '/usr/share/GeoIP/GeoIP.dat'
# temp file -- MUST BE on same filesystem as $outfile
$tmpfile = '/usr/share/GeoIP/GeoIP.dat.tmp'
require 'digest/md5'
require 'open-uri'
require 'zlib'
require 'stringio'
# Fetch GeoIP country file from MaxMind
def get_result_for(key, md5) #{{{1
url = "ht" + "tp://www.maxmind.com/app/update?"
url += "license_key=#{key}&md5=#{md5}"
content = nil
open(url) do |io|
compr = StringIO.new(raw = io.read)
if compr.read(2) == "\x1f\x8b"
compr.rewind
gz = Zlib::GzipReader.new(compr)
content = gz.read
gz.close
else
content = raw
end
end
content
end # }}}1
puts "Begin." if $VERBOSE
begin
omd5sum = Digest::MD5.hexdigest(File.open($outfile, 'r').read) rescue nil
content = get_result_for($license_key, omd5sum)
if content =~ /No new updates available/
puts "No new updates ..." if $VERBOSE
exit 0
end
md5sum = Digest::MD5.hexdigest(content)
content2 = get_result_for($license_key, md5sum)
rescue
puts "Error: Problem fetching file! >> #{$!} (#{$!.class})"
exit 1
end
puts "Fetched." if $VERBOSE
if content2 =~ /No new updates available/
begin
File.open($tmpfile, 'w') do |f|
f.write(content)
end
File.unlink($outfile) if FileTest.exists?($outfile)
File.rename($tmpfile, $outfile)
rescue
puts "Error: Problem updating file! >> #{$!} (#{$!.class})"
exit 1
end
else
puts "Error: Problem refreshing GeoIP -- new file fails MD5 check!"
exit 1
end
puts "Updated." if $VERBOSE
exit 0