Skip to content

Instantly share code, notes, and snippets.

@june29
Created November 26, 2008 00:34
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save june29/29194 to your computer and use it in GitHub Desktop.
Save june29/29194 to your computer and use it in GitHub Desktop.
require "net/http"
require "time"
require "digest/sha1"
Net::HTTP.version_1_2
class HatenaBookmark
def initialize(username, password)
@username = username
@password = password
end
def post(entry)
request = Net::HTTP::Post.new("/atom/post")
request["User-Agen"] = "Ruby/#{VERSION}"
request["X-WSSE"] = hatena_wsse_header()
summary = entry.tags.map {|tag| "[#{tag}]"}.join("") + entry.comment
request.body = <<-"BODY"
<entry xmlns="http://purl.org/atom/ns#">
<title>#{entry.title}</title>
<link rel="related" type="text/html" href="#{entry.url}" />
<summary type="text/plain">#{summary}</summary>
</entry>
BODY
response = Net::HTTP.start("bbeta.hatena.ne.jp", 80) { |http|
http.request(request)
}
end
# http://d.hatena.ne.jp/toward/20051225/ruby_hatena_wsse
private
def hatena_wsse_header
nonce = Array.new(10){ rand(0x100000000) }.pack("I*")
nonce_base64 = [nonce].pack("m").chomp
now = Time.now.utc.iso8601
digest = [Digest::SHA1.digest(nonce + now + @password)].pack("m").chomp
credentials = sprintf(%q[UsernameToken Username="%s", PasswordDigest="%s", Nonce="%s", Created="%s"],
@username, digest, nonce_base64, now)
return credentials
end
end
class Entry
attr_accessor :title, :url, :comment, :tags
def initialize(title, url, comment, tags = [])
@title = title
@url = url
@comment = comment
@tags = tags
end
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment