ブロガーのためのソースコード管理システムをみんなで考えませんか?
id:hakobe932のエントリ「未踏ユースに採択されました」でブロガーのためのソースコード管理システムがIPAの未踏ユースに採択されたそうで、とても興味深いです。
どんなシステムなのか?
ブログにコードを貼付けてもいまいち使い勝手悪いよなー、と普段から気になっていたことを解決するためのシステムを提案してみました。
つまり、私が解釈するに、
「ブロガーが公開するソースコードの再利用性を高めるためのシステム」
ということ(かな?)。
こういうのは、実際のブロガー同士でアイデアを出し合い、議論するのが良いのではないかという、いわゆる集合知の新しいアウトプットとしてはどうでしょうか?(オープンソースプロジェクトみたいに)
特にはてダの場合、技術者が多いように思うので、こういうネタは議論も盛り上がりやすいように思います。
ということで、
Blogramming Project
を提案します。
id:hakobe932さんに拒否されたり、盛り上がらなければボツですが…。
議論する具体的な内容は、
1.要望(こういうのがあればいいな)
2.情報(こういうのがあるらしいよ)
3.提案(こうすればもっとよくならない?)
4.方法(これを利用すれば実現できるかも)
こういった感じでしょうか?
id:hakobe932さんが実際、どういうアイデアを持っているのか分かりませんが(できれば公開して欲しい)、僕のアイデアはこうです。
転載機能
流行りの転載問題ですw
ソースを登録・管理する管理サーバは必要で、そこから転載できるようにする。
転載はソースコードのみ(?)。編集不可(?)。
ソースコードの添削をしたり、このソース使わせてもらいましたー的な転載によるブログエントリが可能。
もちろん、ソース公開者へのリンクが維持される必要がありますが。
ソースコードを登録し、利用してもらう代わりに、自分のブログへトラフィックを誘導できるというメリットがあります。
もしくは添削してもらえた場合は、勉強にもなる。これはWikipediaのようなシステムのイメージです。
もちろん、開発にダイレクトに利用もできる。これによりサービスの立ち上げスピードが格段に向上すると思います。
このアイデアのもとは、「○○を作ってみました」系ブログでよく見る「これには△△と××のライブラリを使っています。」という記述から、それを見たとき「へ〜!そんなライブラリ知らなかった!調べてみよう」という知的好奇心をくすぐってくれる体験です。
さらに、この転載機能をベースにしたアイデアは
CodeRank
です。
つまり、より多く転載されているソースコードが良いコードだという前提でPageRankよろしくCodeRankを付けるのも良いかもしれません。
勉強するときは良質のソースによるコードリーディングが良いとされていますから、このCodeRankで勉強の効率が上がりそうです。
もちろん、システム構築のヒントにもなりそうです。
そして、ランキングの高いプログラマーは満足感と共にモチベーションも向上するでしょう。
どうでしょう?
ブロガーの皆さんも議論してみませんか?
盛り上がって、良いシステムが出来上がれば嬉しいです。
というか僕はとても楽しみにしています。
LightShop2.0 - スライドショー自動生成
Photoshopの「Web フォとギャラリー」機能とLightBox2.0を使って、スライドショーを自動生成できるようになりました。
これはLightShopのバージョンアップ版です。「2.0」はLightBox2.0の「2.0」です。
言い訳っぽいですか?でも恥ずかしいので言い訳させて下さいw
ではデモサイトをどうぞ。
こんなのがあっという間にできます。
使い方
これも以前のエントリと同じです。
参考に、上のデモサイトを作ったパラメータ設定のスナップショットを載せておきます。
指定したフォルダにHTML等が生成されます。
指定したフォルダをサーバにアップロードすればスライドショーのページが出来上がり。
Webデザインが気に入らなければ自分でスタイルシートを編集して下さい。
関係リンク
- LightBox2.0: スライドショーのライブラリです。
- LightShop: LightShopの初期版です。
- LightShopJ: LightShopのジョジョ版です。
rootじゃなくてもgRubyを使いたい
上級者さん、せっかちさんは簡易版をどうぞ。
gRubyとは
gRuby(ぐるびー)とはGD*1というネイティブライブラリのRuby用インタフェースRuby/GDのラッパーライブラリです。
Ruby/GDを簡単に扱えるようにしてくれている有り難いライブラリなのです。
では、これからLinux環境のもとインストール作業です。
Ruby/GDをインストールする
gRubyを使うために、根っこになるRuby/GDをコンパイルしてインストールします。
Ruby/GDを入手する
まずはRuby/GDをダウンロードしてきます。
本家はRAA - ruby-gdなのですが、なぜかソースコードがリンク切れなので、
ここ→http://raa.ruby-lang.org/cache/ruby-gd/からダウンロードしてきます。
ちなみに、ダウンロードしてきたreadme.jaというファイルに記載されている最新バージョンの入手先URLもリンク切れでした。
では解凍します。
% tar zxvf ruby-GD-0.7.4-1.tar.gz
Ruby/GDをコンパイル
ではネイティブライブラリを作成します。
% cd ruby-GD-0.7.4 % ruby extconf.rb [options...] % make # make install
という風にdoc/INSTALL.jaに書いています。
今回はroot権限が無い状態でgRubyをインストールすることが目標なので、少し変更します。
% cd ruby-GD-0.7.4 % ruby extconf.rb --with-ttf --with-freetype --with-jpeg --enable-gd2_0 % make
オプションはgRubyがサポートする機能を余すとこなく利用できるようにするモノです。
これで「GD.so」というダイナミックライブラリが出来ているはずです。
Ruby/GDをインストール
doc/INSTALL.ja通りに「make install」すると「/usr/local/lib/ruby/site_ruby/1.8/」等にコピーされるのですが、
それにはroot権限が必要です。
root権限が無ければここで諦めなければならない所ですが、諦めません。
ではどうするか、
答えは簡単。ローカルにライブラリを用意すれば良いのです。
今回は「/home/adamrocker/lib/ruby」にしましょう。
このディレクトリはどこでもOKです。最後にライブラリパスを通しますので。
では、あらためてインストール。
% cp GD.so /home/adamrocker/lib/ruby
そしてRubyのライブラリパスを通します。
「~/.bashrc」とか「~/.cshrc」などのログインシェルの設定ファイルに環境変数を定義します。
「~/.bashrc」なら
export RUBYLIB=/home/adamrocker/lib/ruby
「~/.cshrc」なら
setenv RUBYLIB=/home/adamrocker/lib/ruby
設定を反映させます。
「~/.bashrc」なら
% source ~/.bashrc
「~/.cshrc」なら
% source ~/.cshrc
これでRuby/GDのインストール完了。
gRubyをインストールする
Ruby/GDのインストールが完了したところで、ようやくgRubyをインストールしましょう。
こちらは凄く簡単です。
gRubyを入手する
まずはgRubyを入手してきます。
そして、解凍・展開です。
% tar zxvf gruby-0.0.1.tar.gz
これでgruby-0.0.1というディレクトリが作られます。
gRubyをインストール
README.ja.rdの通りだとこうなります。
% ruby setup.rb config % ruby setup.rb setup # ruby setup.rb install
またもやroot権限を要する「#」が出てきました。
しつこいようですがroot権限を持ってません。
なので、少しオプションを加えます。
% ruby setup.rb config --prefix=/home/adamrocker/lib/ruby % ruby setup.rb setup % ruby setup.rb install
Linuxのインストール作業ではおなじみの「--prefix」です。
インストールディレクトリを指定できますので、ローカルのライブラリディレクトリを指定しています。
これで「/home/adamrocker/lib/ruby/lib/ruby/site_ruby/1.8/grb」なんていう長ったらしいディレクトリが出来上がってます。
こんなに深くなくて良いので、とりあえずコピーしちゃいます。
% mv /home/adamrocker/lib/ruby/lib/ruby/site_ruby/1.8/grb /home/adamrocker/lib/ruby
これにてgRubyのインストール作業は終わりです。
確認のため、gRubyに付いてくる「example/font.rb」などを実行してみて下さい。
% ruby font.rb
「font.png」が出来ていれば成功です。
それではサヨナラ。
超簡易版gRubyインストール方法
コンパイル、インストールなんて説明イラネ。って人用。
Ruby/GD
入手
http://raa.ruby-lang.org/cache/ruby-gd/
コンパイル & インストール
% tar zxvf ruby-GD-0.7.4-1.tar.gz % cd ruby-GD-0.7.4-1 % ruby extconf.rb --with-ttf --with-freetype --with-jpeg --enable-gd2_0 % make % cp GD.so ${HOME}/lib/ruby
Rubyライブラリパス
export RUBYLIB=${HOME}/lib/ruby
or
setenv RUBYLIB=${HOME}/lib/ruby
gRuby
入手
http://gruby.sourceforge.jp/
コンパイル & インストール
% tar zxvf gruby-0.0.1.tar.gz % cd gruby-0.0.1 % ruby setup.rb config --prefix=/home/adamrocker/lib/ruby % ruby setup.rb setup % ruby setup.rb install
Rubyライブラリパス
export RUBYLIB=${RUBYLIB}:${HOME}/lib/ruby/lib/ruby/site_ruby/1.8
or
setenv RUBYLIB=${RUBYLIB}:${HOME}/lib/ruby/lib/ruby/site_ruby/1.8
超簡単インストールのグラフィックライブラリ「PureImage」
GDはネイティブライブラリなので、コンパイルが必要なのでインストールに少し手間がかかります。
そもそも、Rubyは楽しいプログラミングライフを提供してくれているのに、インストールに時間を食われるのはストレスだ!
もっと気軽に使いたいね!って人がPure Rubyで画像生成ライブラリ「PureImage」を作ってくれています。
こちらはインストール作業がコピーだけというステキな仕様です。
制作者自信が公開していることですが、現状いくつか問題点があります。
- ドキュメント不足
- 動作が重い(ToDo: パフォーマンスチューニング)
- フォントを自分で作る必要がある(Javaで作る)
この問題点が問題と感じない人は是非PureImageを使ってみて下さい。僕も使ってみましたが凄い簡単に使えて楽しいです。
*1:GDとはグラフィック生成ライブラリです。本家 - http://www.boutell.com/gd/
はてなのasin記法をテスト
連続して下のように書いてみる。
asin:4761263199:detail isbn:9784839921996:detail asin:4569657745:detail asin:4091810330:detail
結果どうなってるかな?↓
- 作者: 江村林香
- 出版社/メーカー: かんき出版
- 発売日: 2006/03/20
- メディア: 単行本(ソフトカバー)
- 購入: 2人 クリック: 18回
- この商品を含むブログ (19件) を見る
- 作者: 関正秀,加藤貴之,まえだひさこ
- 出版社/メーカー: 毎日コミュニケーションズ
- 発売日: 2006/11
- メディア: 単行本
- 購入: 1人 クリック: 67回
- この商品を含むブログ (8件) を見る
- 作者: 結城未来
- 出版社/メーカー: PHP研究所
- 発売日: 2006/11
- メディア: 新書
- 購入: 18人 クリック: 209回
- この商品を含むブログ (103件) を見る
鉄コン筋クリートall in one (ビッグコミックススペシャル)
- 作者: 松本大洋
- 出版社/メーカー: 小学館
- 発売日: 2006/12/15
- メディア: コミック
- 購入: 5人 クリック: 47回
- この商品を含むブログ (101件) を見る
次は、何かコメントを入れてみる。
asin:4761263199:detail 著者の実体験を踏まえたビジネス書。よくあるビジネス書スタイルだが、著者の経歴がすごい。短大家庭教師で月給60万。新卒で役員になる最短距離。理想の旦那を見つける契約書。どれも面白そうです。 isbn:9784839921996:detail Amazon、Google、Yahoo!、はてな、YouTube、FlickrなどのWebAPIを利用し、実際にマッシュアップでサービスをくみ上げるHowTo本。各APIのメソッド一覧表等もあり、勉強し終わった後は辞書として使えそう。 asin:4569657745:detail 日本は照明に関して弱いらしい。もっと照明を効果的に使えばクリエイティブなれたりポジティブになれたりリラックスできたり…。人生を豊かにする方法が学べそうです。 asin:4091810330:detail コミック「鉄コン筋クリート」3冊を1冊にした本書。ピンポンの著者。著者書き下ろしのピンナップも付いている。映画連動企画なので逃すと後が無いかも・・・
どうだろう?↓
- 作者: 江村林香
- 出版社/メーカー: かんき出版
- 発売日: 2006/03/20
- メディア: 単行本(ソフトカバー)
- 購入: 2人 クリック: 18回
- この商品を含むブログ (19件) を見る
- 作者: 関正秀,加藤貴之,まえだひさこ
- 出版社/メーカー: 毎日コミュニケーションズ
- 発売日: 2006/11
- メディア: 単行本
- 購入: 1人 クリック: 67回
- この商品を含むブログ (8件) を見る
- 作者: 結城未来
- 出版社/メーカー: PHP研究所
- 発売日: 2006/11
- メディア: 新書
- 購入: 18人 クリック: 209回
- この商品を含むブログ (103件) を見る
鉄コン筋クリートall in one (ビッグコミックススペシャル)
- 作者: 松本大洋
- 出版社/メーカー: 小学館
- 発売日: 2006/12/15
- メディア: コミック
- 購入: 5人 クリック: 47回
- この商品を含むブログ (101件) を見る
はてブRSSの要素を取得するRubyプログラム
はてブ(はてなブックマーク)のRSSを取得して、要素を抽出するRubyプログラムを作ってみました。
はてブのRSS
はてブの
- タイトル (title)
- リンク (link)
- 説明 (description)
あとは各ブックマークの
- タイトル (title)
- リンク (link)
- 説明 (description)
- ブクマした時間 (date)
- 追加したユーザ名 (creator)
- タグ (tags)
他に色々要素がありますが、上記の要素を組み合わせると大抵出来上がるモノなので、コアとなる要素はこれぐらいでしょうか*1。
データ設計
ここからコーディング。まずはデータ設計です。
はてブの情報を格納するクラスを定義します。
# Hatena Bookmark RSS Data Class class HatebRSS attr_accessor :title, :link, :description, :items def initialize @title = @link = @description = nil @items = Array.new end end
ここでitemsはブクマしたそれぞれのサイト情報を格納する配列とします。
インスタンス変数を定義するとgetterとかsetterとかのアクセスメソッドの定義が面倒ですが、
Rubyは内部的に定義してくれる「attr_***」って修飾子があって便利です。
インタプリタ実行時にこの修飾子が付けられたインスタンス変数へのアクセスメソッドが自動で定義されます(きっと…)。
getterのみの定義はattr_reader、setterのみの定義はattr_writerで両方を定義したい場合はattr_accessorです。
話がそれました。次に、その配列の要素となるブクマの情報を格納するクラスを定義します。
# Hatena Bookmark Data Class class HatebItem attr_accessor :title, :link, :description, :date, :creator, :tags def initialize @title = @link = @description = @date = @creator = nil @tags = Array.new end end
tagsが唯一複数出現する可能性があるので配列にします。
データ取得と構築
あとは、RSSを取得しHatebItemオブジェクトを構築して、それをHatebRSSのitems配列に詰め込んでいくだけです。
ここがメインの処理です。
require 'open-uri' require 'rss/1.0' require 'rss/dublincore' # Open XML(RSS) and Make RSS Object bookmark = "http://b.hatena.ne.jp/jkondo/rss" #jkondoのはてブRSS rss = open(bookmark){ |file| RSS::Parser.parse(file.read) } # Set Output Encoding rss.output_encoding = "EUC-JP" # Set HatebRSS instance field hateb = HatebRSS.new hateb.title = rss.channel.title hateb.link = rss.channel.link hateb.description = rss.channel.description # Set HatebItem instance field rss.items.each{ |item| hi = HatebItem.new hi.title = item.title hi.link = item.link hi.description = item.description hi.date = item.dc_date hi.creator = item.dc_creator item.dc_subjects.each{ |tag| hi.tags << tag.content } hateb.items << hi }
open(bookmark){ |file| ... }
はてブはブクマのタグがdublincoreのsubject要素なので、読込むライブラリに注意します。
require 'rss/1.0' require 'rss/dublincore'
RSSの各要素へのアクセスにはRSS Parser標準ライブラリを利用します。
RSS::Parser.parse(file.read)
デフォルトではparseの第二引数はtrueがセットされ、RSSのバリデーション(構文チェック)が実行されます。
怪しいRSSでも取得したい場合はバリデーションをfalseにすると良いです。
少しでも高速にしたい場合も役に立つのかも?(パフォーマンス比較をしていないので分かりませんが…)
RSS::Parser.parse(file.read, false)
私の作業環境に依存して、出力文字エンコードをEUC-JPにしています。
rss.output_encoding = "EUC-JP"
テスト
# Test output puts hateb.title puts hateb.link puts hateb.description puts "------" hateb.items.each { |hi| puts hi.title puts hi.link puts hi.description puts hi.date puts hi.creator hi.tags.each{ |tag| print tag, ", " } puts "", "------" }
jkondoのブックマーク http://b.hatena.ne.jp/jkondo/ jkondoのブックマーク ------ NHKスペシャル|グーグル革命の衝撃 〜あなたの人生を“検索”が変える〜 http://www.nhk.or.jp/special/onair/070121.html 2007-01-14T17:29:12+09:00 jkondo ------ The Apple iPhone - Engadget http://www.engadget.com/2007/01/09/the-apple-iphone/ 2007-01-10T04:24:38+09:00 jkondo ------ CYCLINGTIME.com : 神宮外苑でクリテリウム開催 学連70周年記念行事 http://www.cyclingtime.com/modules/ctnews/view.php?p=3784 2006-12-28T01:09:07+09:00 jkondo これはすごい, ------ (略)
意外とコメントもタグも付けてないブクマが多いんですね…。
ということで、今回ははてブのRSSの各要素にフルアクセスするRubyプログラムを作ってみましたというエントリでした。
全プログラムを提示しておきます。
全プログラム
require 'open-uri' require 'rss/1.0' require 'rss/dublincore' # Hatena Bookmark RSS Data Class class HatebRSS attr_accessor :title, :link, :description, :items def initialize @title = @link = @description = nil @items = Array.new end end # Hatena Bookmark Data Class class HatebItem attr_accessor :title, :link, :description, :date, :creator, :tags def initialize @title = @link = @description = @date = @creator = nil @tags = Array.new end end # Open XML(RSS) and Make RSS Object bookmark = "http://b.hatena.ne.jp/jkondo/rss" rss = open(bookmark){ |file| RSS::Parser.parse(file.read, false) } # Set Output Encoding rss.output_encoding = "EUC-JP" hateb = HatebRSS.new hateb.title = rss.channel.title hateb.link = rss.channel.link hateb.description = rss.channel.description # Set HatebItem instance field rss.items.each{ |item| hi = HatebItem.new hi.title = item.title hi.link = item.link hi.description = item.description hi.date = item.dc_date hi.creator = item.dc_creator item.dc_subjects.each{ |tag| hi.tags << tag.content } hateb.items << hi } # Test output puts hateb.title puts hateb.link puts hateb.description puts "------" hateb.items.each { |hi| puts hi.title puts hi.link puts hi.description puts hi.date puts hi.creator hi.tags.each{ |tag| print tag, ", " } puts "", "------" }
10行で書くProxyサーバ越えのRubyプログラム
Proxyサーバを経由してあるサーバにリクエストを送りたい場合、のプログラムを書いてみた。
require 'net/http' proxy_host = "#{プロキシサーバのドメイン}" proxy_port = "8080" #たいてい8080ポート host = "#{接続先ドメイン}" path = "#{アクセスしたいファイル}" Net::HTTP.version_1_2 puts Net::HTTP.Proxy(proxy_host, proxy_port).start(host){ |http| http.get(path).body }
ちなみにProxyサーバにログイン認証が掛かっている場合はこちら↓。
require 'net/http' proxy_host = "#{プロキシサーバのドメイン}" proxy_port = "8080" proxy_user = "#{ユーザ名}" proxy_passwd = "#{パスワード}" host = "#{接続先ドメイン}" path = "#{アクセスしたいファイル}" Net::HTTP.version_1_2 puts Net::HTTP.Proxy(proxy_host, proxy_port, proxy_user, proxy_passwd).start(host){ |http| http.get(path).body }
11行になっちゃうけど、上のと平均すると10行だからイイかw
ちなみにgetした内容に日本語が含まれると文字エンコードする必要があります。
(注)パスワードが平文で流れることに対する危険性を十分認識して、ご利用は自己責任で。
Amazon Web Serviceを使ってISBN-13からASINを取得するRubyプログラム
「Amazon Web Servicesを使ってISBN-13からASINを取得するPerlプログラム」をRubyで実装することで勉強させていただこうと思います。
言語仕様が少々違っても、コーディング規約に学ぶ点は多いはず。
ということでAmazon Web ServicesのE-Commerce Serviceを使って、ISBN-13からASINを取得するRubyプログラムを作ってみました。
require 'rexml/document' require 'open-uri' require 'kconv' aws_access_key_id = 'あなたのAccessKeyId' # For debug OUTPUT_ENCODING = 'EUC-JP' # 現状意味をなしていません(汗) # Set up ISBN. isbn = '9784798111117' #『オブジェクト指向入門 第2版 原則・コンセプト』のISBN-13 # Set up URL. request_url = 'http://webservices.amazon.co.jp/onca/xml' option_list = [ "Service=AWSECommerceService", "AWSAccessKeyId=#{aws_access_key_id}", "Operation=ItemLookup", "IdType=ISBN", "ItemId=#{isbn}", "SearchIndex=Books", "ResponseGroup=Request,Small", "Version=2007-01-15" ] # Assemble all options. option_string = option_list.join('&') url = "#{request_url}?#{option_string}" # Retrieve result. puts "ISBN: #{isbn}" response_xml = open(url){ |e| REXML::Document.new e } # Compose output string. output =<<EOD ASIN: #{response_xml.root.elements["Items/Item/ASIN"].text} Title: #{response_xml.root.elements["Items/Item/ItemAttributes/Title"].text} Author: #{response_xml.root.elements["Items/Item/ItemAttributes/Author"].text} EOD print Kconv.toeuc(output)
実行結果です。コマンドラインの都合上EUC-JPにしています。
$ruby amazon_isbn.rb ISBN: 9784798111117 ASIN: 4798111112 Title: オブジェクト指向入門 第2版 原則・コンセプト Author: バートランド・メイヤー
というか、PerlのOUTPUT_ENCODINGに相当するRubyの定数が調べきれませんでした…。
これが分かれば、毎回KconvでEUCにエンコードする必要ないんですけどね。
そして、ここまでやっておきながらトラバで404 Blog Not Foundの中の人が添削をされていました。
Rubyでもあるのかな?option_listをHashにしてみましたが、結局Stringに変換してるので本質的に上と同じ。
どちらでも結果はもちろん同じです。
option_list = { "Service" => "AWSECommerceService", "AWSAccessKeyId" => aws_access_key_id, "Operation" => "ItemLookup", "IdType" => "ISBN", "ItemId" => isbn, "SearchIndex" => "Books", "ResponseGroup" => "Request,Small", "Version" => "2007-01-15" } option_string = option_list.map{|key, val| "#{key}=#{val}" }.join('&')