Python で eRuby を実現するには
インデントベースだとeRubyのようなテンプレートが難しい
Matz日記:PythonをDISる
Python はインデントベースなので、eRuby に限らずコード生成とは全般的に相性が悪い。しかし、eRuby 程度であれば以下のようなルールで実現できる。
- テキストを print 文 (またはそれに相当するもの) に変換するときは、
- 直前の文が「:」で終わっていればインデントを増やす
- それ以外なら直前の文やコメントと同じインデントを使う
- for 文や if 文の終わりは、インデントしたコメントで明示するようにする。
たとえば次の例では、2 行目が「:」で終わっている。そのため、変換された Python コードの 3 行目では、インデントを増やしている。また 5 行目のインデントが戻っているのは、直前 (4 行目) のコメントのインデントに合わせているためである。
### もとのテキスト 1: <ul> 2: <% for item in L: %> 3: <li><%= item %></li> 4: <% #end %> 5: </ul> ### 変換された Python コード 1: print "<ul>", 2: for item in L: 3: print "<li>", item, "</li>" 4: #end 5: print "</ul>"
次の例では、4 行目は「:」で終わってはいない。そのため、変換された Python コードの 5 行目では直前の 4 行目と同じインデントを使っている。
### もとのテキスト 1: <ul> 2: <% i = 0 %> 3: <% for item in L: %> 4: <% i += 1 %> 5: <li><%= i %>:<%= item %></li> 6: <% #end %> 7: </ul> ### 変換された Python コード 1: print "<ul>", 2: i = 0 3: for item in L: 4: i += 1 5: print "<li>", i, ":", item, "</li>" 6: #end 7: print "</ul>"
Makoもそうですが、end明示するのは「工夫」とは言えないのでは。
Matz日記:PythonをDISる
eRuby のようなツールでは、Python のインデント方式は利用できない。
また eRuby と同じようにテキスト汎用にしようとすると、for 文や if 文では「範囲」を指定しなければならず、どうしても「end」のようなものが必要になる。
だから、Mako や pyTenjin で「end」をつけるのは、工夫ではなくて「必然」(あるいは「必要悪」) といえる。
このへんは、確かに Python と eRuby もどきは相性が悪いと言えるが、「end」をつけるだけで回避できるのであれば、そう大きな欠点ではないと思う。