Subscribed unsubscribe Subscribe Subscribe

PHP をテンプレートエンジンとしてもっと頑張らせるパッチ

これは発表中に紹介したものだけど、「意欲的」な内容の割におもしろさが伝わらなかった気がするので改めて紹介。

  • きょうび論理構造を無視して、純粋に入力を文字列として扱うテンプレートエンジンっていらねーって思いませんか?
  • PHP はテンプレートエンジンとしてもっと進化するべきと思いませんか?

ということなので、

<?php $a = << ?>
<?html>
  <head>
  </head>
  <body>
    <?div id="{$a}" style="...">
    </?div>
  </body>
</?html>
<?php var_dump($a); ?>

のようなテンプレートを解析して、直接配列として変数に突っ込めるパッチを書いたという話。

要は

<?html>
  <head>
  </head>
  <body>
    <?div id="{$a}" style="...">
    </?div>
  </body>
</?html>

のように

<?...> </?...>

で囲まれた箇所が

<?php $... = << ?>

というような記述の後に続いていると、これを XML リテラルのようにテンプレートの一部と解釈して、<?...>のような特殊タグで表現された論理構造を DOM のような格好で array にして $... に突っ込むというような機能を実装したっていう話です (こりゃ分かりづらいよな)。

ちなみに上のコードを実行すると、

array(3) {
  ["name"]=>
  string(4) "html"
  ["attrs"]=>
  array(0) {
  }
  ["contents"]=>
  array(3) {
    [0]=>
    string(33) "
  <head>
  </head>
  <body>
    "
    [1]=>
    array(3) {
      ["name"]=>
      string(3) "div"
      ["attrs"]=>
      array(2) {
        ["id"]=>
        object(Closure)#1 (1) {
          ["static"]=>
          array(1) {
            ["a"]=>
            NULL
          }
        }
        ["style"]=>
        string(3) "..."
      }
      ["contents"]=>
      array(1) {
        [0]=>
        string(5) "
    "
      }
    }
    [2]=>
    string(11) "
  </body>
"
  }
}

となります。

特殊タグ <?...> 中の属性値が "{...}" のような形式を取っているとき、... は PHP のコードと解釈され、そのコードを実行した値がそのまま埋め込まれ…るのではなく、これを自動的にクロージャ化して、それを属性値の値とする、という仕様だったりします (使われている変数は自動的に外部のスコープから取り込まれる)。なのでレンダリングまで評価を遅延できるのと、レンダリング時に必要に応じてエスケープしたりもできるわけですね!!!!

↓以下diff