15 min/d

ぼうずやのにっき

Matt-Esch/virtual-dom をよんだ

2016-01-25 と今日で Matt-Esch/virtual-dom を読んだ。

Matt-Esch/virtual-domfacebook/react を参考につくられた Virtual DOM の実装のひとつ。cyclejs/cycle-domRaynos/mercury などで利用されている。facebook/react よりも source code の量が少ない。おそらく簡素で理解しやすいだろう。

今回の目的は Virtual DOM の実装の理解を深めることだ。これは今週の目標 (2016-01-24) のとおりだ。どのように差分を検出・適用するのかを知りたい。また cyclejs/cycle-dom はそれをどう利用しているのか。Rx と Virtual DOM をどう結合しているのかも知りたい。

Matt-Esch/virtual-dom は vdom / virtual-hyperscript / vnode / vtree をまとめたものだ。別 npm package になっていたりもするが、他の repository の更新は止まっているように見えるので virtual-dom repository に統合したのかもしれない。

vdom は creteElement / patch という Virtual DOM から Element の生成と Element への patch の適用処理がある。

virtual-hyperscript は Virtual DOM の生成用の DSL を提供する。cyclejs/cycle-domh でおなじみのものだ。

vnode は Virtual DOM の構造やその差分を表現する VNode (Virtual Node) / VText / VPatch などを含んでいる。

vtree は Virtual DOM 間の差分を検出する diff を含む。

まとめると virtual-hyperscript で Virtual DOM を生成し、 Virtual DOM を createElement で Real DOM を生成する。 diff で Virtual DOM 間の差分を得て、patch で Real DOM に差分を適用する。

まずは構造を提供する vnode から。ここは特に触れるところがない。version および type を持っていたり Thunk や Widget は render などを持っていることくらいか。

次に virtual-hyperscript 。ここでは key 属性 namespace 属性 ev-* 属性を特別扱いしている点や focus に気をつかっている点などが気になった。VNode / VText 以外は生成していないように見える。ほかに Widget と VThunk があるはずなのだけど……。Widget は利用者側で独自の要素を埋めるために使うはず……。

vtree の diff 。ここは重要だ。 2 つの Virtual DOM tree を取る。walk で親から子へと走査する。ざっと読んだ印象なのだけどあまり細かい比較をしていないように見える。同じ階層にある要素を比較して位置と変更内容を表す VPatch を集めていく感じかな。読み違えてるかも。階層がすこし変わるとごっそり捨ててしまいそうな気がする。

最後は patch 。domIndex で要素と index を patch に関係のある部分だけ取得して適用する点が特徴かな。

もうすこし詳しく読んだほうが良さそうだけど、ひとまず cyclejs/cycle-dom に進もうと思う。