Ruby言語やLinuxのネタが多いです。
November 01, 2005 [おもひで]
■ 自分への戒めのために今回のバグについてメモしておく。
このバグは0.14.0で作り込んでしまったバグで、元々は前回のこの問題に対処しようとしたもの。
前回の考察で、全てのメソッド毎にこういった改修をやるのはものすごく大変なので代替案が無いかなぁ、と思って探していたところ、これだっ!とひらめいたのが0.14.0での実装....なんだけどこれがダメだったわけよ。なんで気づかないかなー、オレ。
で、具体的には、
「GLib::Objectが生成された際に、とにかくRubyのグローバルなHash変数にその値を保持する。g_object_unrefが呼ばれてリファレンスカウンタが0になったタイミングでRubyのHash変数からもオブジェクトを削除するようにする。」
という実装。
当時は、Gtk::Object#destroyやg_object_unrefなんかが呼ばれるタイミングで削除できるから問題ない、と思ってしまっていたし、なんとなくテストしている範囲では大丈夫だった(ような気がした)ので問題ないと思ってたんだけど、実はg_object_unrefが呼び出されるタイミングって、RubyオブジェクトがGCされるタイミングなわけで、それってグローバルなHash変数に保持する以上、GCされないんだよね。うぬぬ。なぜ気づかなかったんだ....。
やはり、前回のこの問題をきちんと考えないといけないんだろうなぁ。
■ [Ruby-GNOME2] G_RELATIVE2
前回の考察でG_RELATIVE2を使う、と書いてある。ちょっと実装見直してみたけど、このまま使うのは正直しんどいなぁ。
名前も含めて考え直さないとだね...。
November 04, 2005 [おもひで]
■ [Ruby-GNOME2] YASW - Yet Another Stock Watcher
株価を見るアプリケーションだそうです。Ruby/GTK2, Ruby/Libglade2を使って頂いてます。
November 05, 2005 [おもひで]
■ [Ruby] sfmltoj-1.2
ちとRuby-GNOME2 MLのアーカイブの調べ物をしようとして過去ログを見ようとしたら、トップページ以外はことごとく表示できないようになっていたので、修正版をリリースしました。
おそらく、SF.net周りは全滅だとおもわれるのでsfmltojを使っている方はぜひバージョンアップしてください。
■ SF.net自体がバージョンアップしたのかなぁ。どうせなら日本語がきちんと表示できるようになればいいんだけどな。
November 06, 2005 [おもひで]
■ [Ruby-GNOME2] libgdaがSuSE 10.0でコンパイルできない
日曜日にRuby-GNOME2-0.14.1リリースしようと思ってたんだけど、結局、この不具合が解決できず。
最初、Fedora Core 4の環境にlibgda-1.3.91を野良ビルドしてRuby/Libgdaをコンパイルしてみたんだけど、問題なく動作する。
うーん、と悩んだあげく、結局、SuSE 10.0の環境を作ってみてみることにした。
で、これだけでも時間かかったんだけど、結局大きな問題があることがわかった。
つまり、libgda-1.2とlibgda-2.0(libgda-1.3.91)のAPIの非互換性だ。Fedoraの野良ビルドでは、前バージョン(libgda-1.2)が残っていたので問題なくコンパイルできちゃってた。pkg-configのパッケージ名も変更になっている(libgda → libgda-2.0)。
うーん、これ直してからリリースするの結構面倒くさいなぁ。今のところどれくらいAPI変更が行われたのか定かではないのでどれくらい時間かかるかわかんないしね。
■ でも、SuSE 10.0ってstable版なんだよね。
だとしたらやっぱりサポートしないといかんだろうなぁ。ロラン最近音沙汰ないしなぁ。うー(T_T)。
#ってか、stable版に1.3系入れないで欲しいよなぁ。
■ そうそう、今回SuSE始めて入れてみたんだけど、インストーラがKDEベースなのか全然Fedoraと違う。そのほか、デフォルトの壁紙とか、なんとなく全般的におしゃれで良い感じだ。
■ ってか、ひとまず今日は寝よう...(=o=)zZZZ。
November 14, 2005 [おもひで]
■ [Ruby-GNOME2] Ruby-GNOME2-0.14.1
リリースしました。メモリリークバグを修正しています。
0.14.0を使っている方はなるべく早めに0.14.1にアップデートしていただくようお願いします。
なお、このバージョンではlibgda-1.3.9x対応をしていません。libgdaを使う場合は1.2.x系を利用してください。
November 15, 2005 [おもひで]
■ [Ruby-GNOME2] Gnome Splash Properties-0.2.1
Splashプロパティ設定ツール。Ruby/GTK2, Ruby/GConf2, Ruby/GnomeVFSを使って頂いています。Gnome-Artにちょっと系統が近いかな。こういう設定周りのツールは性能を要求される場面が少ないのでスクリプト言語には向いているよね。
November 20, 2005 [おもひで]
通常:
puts "name = %s, %s" % ["Masao", "Mutoh"]
新:
puts "name = :first, :family" % {:first => "Masao", :family => "Mutoh"}
このアイデア自体は以前もどこかで話題になってたような気もしないでもないんだけど、まぁ、そのときは別に無くてもイイじゃん、的に感じてた。 でも、これ、Ruby-GetText-Packageの翻訳者という立場で考えると、後者の方が圧倒的にわかりやすくなる、ってことに今更ながら気づいた。
■ Ruby-GetText-Packageでは、翻訳者はpoファイルというカタログファイルを編集していく。これが以下のようになる。
通常: msgid "name = %s, %s" msgstr "名前 = %s, %s" 新: msgid "name = :first, :family" msgstr "名前 = :first, :family"
上記の例だと、今のままでは、最初の%sが何で2つめの%sが何を示すのかそれだけではわかりづらい。時には翻訳者自身がソースコードの方を確認しなければわからないかもしれない。それに比べて新しい方は変数名さえ上手につけてあげれば翻訳者にとってかなりわかりやすくなる。
■ さらに、もう一つ利点がある。翻訳先で順序を変更するときだ。上記の例で、日本語の場合は名字と名前は入れ替えて表示したいはず。
通常: msgid "name = %s, %s" msgstr "名前 = %2$s %1$s" 新: msgid "name = :first, :family" msgstr "名前 = :family :first"
こうなると、最初の例に比べ2つめの方が圧倒的にわかりやすい。
class String
alias :_old_format_m :%
def %(args)
if args.kind_of?(Hash)
ret = dup
args.each {|key, value|
ret.gsub!(/:#{key}/, value.to_s)
}
ret
else
_old_format_m(args)
end
end
end
#以下はサンプル
puts "name = %s, %s" % ["Masao", "Mutoh"]
puts "name = :first, :family" % {:first => "Masao", :family => "Mutoh"}
puts "name = %2$s %1$s" % ["Masao", "Mutoh"]
puts "name = :family :first" % {:first => "Masao", :family => "Mutoh"}
■ 実際は、Ruby-GetText-Packageを使うことを想定しているので、サンプル部分は以下のようになる。
puts _("name = :first, :family") % {:first => "Masao", :family => "Mutoh"}
■ 上記の例だと、Hashを使った方では%5.2f等のsprintf記法の大半が使えなくなってしまうのが難点と言えば難点か...。でも、かなり良い感じだ。実際にRuby-GetText-Packageに実装してみようかしらん。
■ おっと、忘れてた。そんなことなら、最初から#{first}ってやればいいじゃん、と思うかもしれないけど、#{...}が評価される順番の関係でRuby-GetText-Packageでは#{...}形式はうまく使えないんだよね。
November 21, 2005 [おもひで]
■ [Ruby] String%(val) の拡張(3)
ZnZさんによると%{...}という記法が良いのではないかとのこと。確かにその通りですね。
昨日の実装でargs.each{...}内の正規表現の部分を↓にすれば良いのかな。
ret.gsub!(/%{#{key}}/, value.to_s)
■ [Ruby-GNOME2] Xiangqi Ascii Board Parser
中国のボードゲーム(Chinese Chessと書いてある)のGUIフロントエンド...みたいです。
今のところ、ASCIIベースの譜面をGUI化する(だけ)みたいですね。メール経由でサーバーにアクセスして対戦するのかな。そこまでGUIフロントエンドとして実装したらおもしろいね。
November 23, 2005 [おもひで]
■ [Misc] のまネコ使用中止求め殺害予告、専門学校生を再逮捕
これって、どうやって専門学生を特定したのかなぁ。
警察が2chからaccess.logを取得
→書き込んだ時のaccess.logからIPアドレスを特定
→IPアドレスが専門学校のアドレスだった
→専門学校ではパソコンの貸し出し記録を持っていた
→専門学生を特定
って感じかな。マンガ喫茶とかからでもパソコンの貸し出し記録があれば特定できるか。
個人宅からの書き込みだとすると固定IP持ってないときついよね。ADSLなんかだったら地域までは絞れるとは思うんだけど....。
プロバイダ側が、いつどの契約者にどんなIPを振り分けた、なんてログを持ってるとか?であれば特定はできるのかな。
まぁ、最近だったら固定IPって可能性もあるか...。
November 25, 2005 [おもひで]
■ [Ruby-GNOME2] Imendio AB announces the GTK+ on Mac OS X port project via 安部さんとこ
こ、こ、これはもしかして、Mac OS X用のGTK+でX Window不要バージョン!?
とうとう、GTK+もマルチプラットフォームを達成できるのか!?
うーん、試したい。マック欲しー。誰かクレー。
November 26, 2005 [おもひで]
■ [Rails] Modelのローカライズ
最新のCVS版Ruby-GetText-Packageを使うと、以下のようにするだけで_("")をはじめとするGetTextなメソッドが使えるようになる。
#app/controllers/application.rb
require 'gettext/rails'
class ApplicationController < ActionController::Base
init_gettext "blog", "UTF-8" # textdomain, charset
end
#app/models/article.rb
class Article < ActiveRecord::Base
validates_presence_of :description, :message => _("can't be empty.")
end
上記はViewでもModelでも同じblogというテキストドメインが使用されるので、poファイルを作るときは全部で1つのblog.poファイルを作ればよい。もちろん、:messageを指定しなければデフォルトのメッセージが(ローカライズされた上で)表示される。
■ そうそう、plugin化するかちょっと迷ったけど、まぁ、しなくてイイかなぁ、と思ってる。だってどうせinit_gettext行を書くなら、ここにrequireも書いちゃった方が、pluginディレクトリ配下にファイルを置くより楽だもんね。
■ それから、第0回 Rails勉強会@東京を参考にしつつ、ActiveRecord本体のエラーメッセージもローカライズできるように変更中。特に、フィールド名のローカライズについて、かなり良さげなアイデアを思いついてしまったのでそれを実装してみようと思う。
これらは、次のRuby-GetText-Packageに含まれる予定。お楽しみに。
November 29, 2005 [おもひで]
■ [Rails] Modelのローカライズ (2)
ActiveRecordのRuby-GetText化をする上で、偶然なんだけど、最近Rails MLで話題のCustom Validation Messages pluginと同等の機能も実装できちゃったことに気づいた。具体的には以下のような感じ。
#app/models/article.rb
class Article < ActiveRecord::Base
validates_presence_of :title, :message => _("%{field_name} can't be empty!")
validates_length_of :description, :minimum => 10,
:message => _("%{field_name} is too short (min is %d characters)")
end
_()で囲わなければCustom Validation Messages pluginとほぼ同様。あとは、"[Cheer up!]"という[]で囲う記法をサポートするとCustom Validation Messages pluginと同機能となる。でも、どうしようかなぁ。
今のところ、後方互換性のために、%{field_name}が無い場合は先頭にfield_nameをつけるという仕様にしているんだよね。
まぁ、要望があったら追加する、ってとこかなぁ。
■ ちと、%{field_name}って長いな。%{fname}にすっかな。それだとfilenameっぽいか。
■ 追記:%{fn}にしてみた。短い方が良いよね。
■ たとえば、上記の(2)のArticleクラスの例で言うと、Articleクラスには一切手を加えずにフィールド名がローカライズされる。
その、ローカライズされるフィールド名はpoファイルに記述されてる必要があるんだけどね(ApplicationControllerのinit_gettextで記述したテキストドメイン、この前の例ではblog)
# po/ja/blog.poの内容に以下を追記。 msgid "Article" msgstr "記事" msgid "Description" msgstr "内容"
■ 実は上記の部分までは実装済み。次のリリースまでに自動抽出機能をrgettextに持たせる予定で、そこまでやれば、開発者はほとんど意識することなくModel部分のローカライズ文字列をpoファイルにはき出すことができてしまうわけだ。
ね。この機能、圧倒的にローカライゼイションのアドバンテージになるでしょ。
■ [Rails] Modelのローカライズ (4)
で、ちょっと悩んだのが、(3)の時のmsgidを素のフィールド名にしておいて良いか、という問題。多くの場合は問題ないと思うんだけど、複数のテーブルに同じ"name"というフィールドがあったとして、それを日本語化したい場合はどうだろう。
場合によっては両方とも「名前」で良いかもしれないけど、もしかしたら違うようにしたいのかもしれないよね。
例えば、ArticleテーブルのnameとGroupテーブルのnameがあったとき、前者は「記事名称」後者は「グループ名」という風に和訳したいかもしれない。
もちろん、元々のテーブル設計がこの違いを意識して分けてれば(前者をarticle_name, 後者をgnameにする等)問題ないんだけど、普通はそんなところをユニークにしたりしないよね。
ってことは、やっぱり、ここはsgettextの登場かな。テーブル名を頭にくっつけて以下のような感じにすっか。
# po/ja/blog.poの内容に以下を追記。 msgid "Article|Name" msgstr "記事名称" msgid "Group|Name" msgstr "グループ名称"
この例では英語版ではどちらも"Name"と表示されることになる。英語の場合はそれで問題ない(RoRの場合、少なくともそこは表示名となるわけだからそれを意識したフィールド名にするはず)はず。でも、さらに、英語でもこの名称を変更したい場合はCかenロケールのpoファイル作ればいいという代替案も提供できるところがこのアイデアのナイスなところ(自画自賛(^^;))。
■ あ、そっか。このアイデアだと、テーブル名・フィールド名毎にhuman_attribute_nameをRDBのテーブル名・フィールド名とは別に定義できる、というのが売りになるね。それがたとえC(en)ロケールであってもね。
■ この辺、今、もりもり実装中なのでアドバイスやグッドアイデアがある人はお早めにご連絡お願いしま〜す。
#といっても、まだ部分的にCVSに反映できてませんが(^^;)。

▲ kou [やろうかと思ってdiffしてみたら結構な量だったのであきらめてしまいました...]
▲ むとう [ぬぬ。そうなんですか... ひとまず、0.14系はLibgda-1.2系で我慢してもらいますか....]