Skip to content

Instantly share code, notes, and snippets.

@aisuii
Created August 17, 2012 11:46
Show Gist options
  • Save aisuii/3378235 to your computer and use it in GitHub Desktop.
Save aisuii/3378235 to your computer and use it in GitHub Desktop.
#!env ruby
# coding: utf-8
require 'irb'
require 'fileutils'
require 'shellwords'
module Service
COOKIE_DIR = File.join(File.expand_path(File.dirname(__FILE__)), '.cookies')
COOKIE_FILE = File.join(COOKIE_DIR, 'hatena.cookie')
LOGIN_PATH = 'https://www.hatena.ne.jp/login'
BASE_URL = 'http://b.hatena.ne.jp'
module_function
def curl(arg)
`curl -s #{arg}`
end
def shesc(str)
Shellwords.escape(str)
end
def init
FileUtils.mkdir_p(COOKIE_DIR)
end
def cleanup
FileUtils.rm_rf(COOKIE_DIR)
end
def login(name, password)
res = curl "-c #{COOKIE_FILE} -d name=#{name} -d password=#{password} #{LOGIN_PATH}"
!res.match(/error-message/)
end
def login?
res = curl "-b #{COOKIE_FILE} #{LOGIN_PATH}"
!!res.match(/oauth-message/)
end
def logout
FileUtils.rm_rf COOKIE_FILE
true
rescue
false
end
def bookmark_confirm(hatena_id, target_url)
confirm_url = File.join BASE_URL, hatena_id, 'add.confirm'
confirm_url += "?url=#{shesc target_url}"
res = curl "-b #{COOKIE_FILE} #{confirm_url}"
rks = $1 if res =~ /name="rks".*value="(\S+?)"/
url = $1 if res =~ /name="url".*value="(\S+?)"/
from = $1 if res =~ /name="from".*value="(\S+?)"/
users = $1 if res =~ /(\d+)\s*users/
tags = res.scan(/class="tag".*?>(\S+?)</)
tags.flatten!
{:rks => rks, :url => url, :from => from, :users => users, :tags => tags}
end
def bookmark(hatena_id, comment, options = {})
post_url = File.join BASE_URL, hatena_id, 'add.edit'
res = curl "-L -b #{COOKIE_FILE} -d rks=#{shesc options[:rks]} -d url=#{shesc options[:url]} -d from=#{shesc options[:from]} -d comment=#{shesc comment} #{post_url}"
if res =~ /link.*rel="canonical".*href="(\S+?)"/
$1
else
"ブックマークできたかわからん"
end
end
def prompt(message)
print "#{message}: "
res = gets
res.chomp
end
# ***** みたいにするやつだれか実装して
def secure_prompt(message)
end
end
module User
module_function
def destroy
FileUtils.rm_rf username_file if File.exists?(username_file)
end
def restore
File.read username_file if File.exists?(username_file)
end
def username_file
File.join(Service::COOKIE_DIR, 'username')
end
def serialize(name)
File.open(username_file, 'wb') {|f| f.write name }
end
end
def usage
print <<-EOL
login:
login with hatena_id and password.
bookmark:
bookmark.
login?:
return login status.
me:
return login user name.
logout:
logout.
cleanup:
cleanup cookie directory.
EOL
end
def me
@me ||= User.restore
end
def login?
Service.login?
end
def login
name = Service.prompt('hatena id')
password = Service.prompt('password')
if Service.login(name, password) and @me = name and User.serialize(name)
'success'
else
'fail'
end
end
def logout
User.destroy
Service.logout
end
def cleanup
Service.cleanup
end
def bookmark
url = Service.prompt('URL')
confirmation = Service.bookmark_confirm(me, url)
puts "#{confirmation[:users] || 0} users bookmark"
unless (tags = confirmation[:tags]).empty?
puts "tags: #{tags.join(', ')}"
end
comment = Service.prompt('comment')
Service.bookmark(me, comment, confirmation)
end
begin
Service.init
IRB.start
# ログインしっぱなしでいいか
#ensure
# Service.cleanup
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment