Node.jsのv0.12の時に harmony はdefaultにならないという結論になりました。

2014/02/01 -- 結論が出たようなので、追記。


あと下記の指摘をいただきまして、少し修正しました。


                                              • -

ここ最近、Node.jsのgithubリポジトリ上でharmonyオプションに関して議論されてて、
この辺り勘違いしている人も多そうなのでこの際まとめようかと。

Node.js 0.12 では yield が使えるのでコールバック地獄にサヨナラできる話 - てっく煮ブログ

去年の6月に公開された記事ですが、この記事を読んでv0.12からはデフォルトでyieldが使えるんだと思った方も多いのではないでしょうか。
結論から言えば、v0.12からharmonyオプションがデフォルトになるという事は決められていません

そもそも、v8側で実行時にharmonyオプションが必要なので、v8のオプションが必要な間はNode.jsでもharmonyオプションをデフォルトにするという判断ができない、というのがこれまでの公式見解でした。

現在のステータスは議論中で、デフォルトはonにしないものの、いくつか選択肢を用意してもいいのではないか、というのが新リーダーである TJ Fontaine の意向です。


現在のステータスとして、harmonyオプションは見送ることになりました。

harmony オプションのおさらい

harmonyオプションとは、node.jsに対してES6で仕様策定中の機能を使えるようにしてくれるオプションです。

koaとかcoなどで使っているgenerator/yieldはES6で定義されている新しいシンタックスなので、harmonyオプションがenableじゃない限りはkoaやcoは実行できません。

逆に言うと、harmonyオプションをenableにした場合、generator/yieldだけじゃないES6の色んな記法が使えるようになります。

letを使うblock scopingmoduleStringの新機能weak mapなんかが使えるようになります。

せっかくなので議論の流れを簡単に翻訳

今でもここで議論中です。
翻訳は間違っている可能性もあるので、間違いを見つけたら報告して下さい。

bnoordhuis (issue opener) :

harmonyオプションをdefaultにするのはv0.12で最も期待されてるfeatureなんじゃないか? これをきっかけにharmonyを使ったライブラリ authorが増えるだろうし、これまでの互換性は --no-harmony オプションにして、互換性を保てるようにしてあげればいいのでは...?

othiym23, domestic :

いやいや、V8でデフォルトになっていないのはNode.jsでもデフォルトにするべきじゃないよ。

そもそもv8のES6実装はかなり酷いものもあるし、ES6の仕様から外れたものもある。リスクがあるからその時期じゃない。

indutny:

v8の実装を待とうじゃないか、そろそろ安定するだろうし、仕様との整合も取れるだろう。

※ここで、一旦issueがcloseされる。

TJ Fontaine:

いや、もう少し議論を進めるためにissueをreopenするよ。

確かにNodeの公式見解としては、v8がサポートするまでNodeでサポートはしないというものだ。
ただそれには反論もあって、現在のnpm packageを検索するとその徴候がわかると思う(多分、harmonyオプションを有効にしないと動かないモジュールに対して言っているんだと思われる。)。

そういう意見に応えるためにもいくつかの折衷案を選択肢として提供するべきだと思うんだ。

自分の意見としては、node_hのようなコマンドを用意して、node_hからnodeが実行されたらharmonyオプションを有効にする、という方針にしようと思っている。

node_hは単なるnodeへのlinkなので、デプロイするのは簡単にできるはずだ。(Nodeがそのリンクを提供しない場合、)リンク自身は npm install -g node_h で提供することもできる。

Nodeがリンクを提供した場合、node_hというメンテナンスしなきゃいけないものが増えるという点はあるが、node_hの中でharmonyの機能として提供するかしないかを判断できるため、harmonyオプションをデフォルトで提供するまでのシナリオを描きやすいという利点もある。

今のところ有効にしないと判断したいものは以下の問題を含んでいるケースだ。

  • まだES6で仕様が決まっていない
  • 実装が済んでいない
  • 既存コードを壊す可能性がある。
  • パフォーマンスを阻害する

これらに含まれる可能性があるのであれば有効にしない方がいいだろう、domenicと検討して、以下のharmonyの機能は有効にする/有効にしないという判断をしている。

  • --harmony_typeof ( typeof セマンティクスを有効にする)
    • -1 (有効にしない、存在しないほうが良い)
  • --harmony_scoping ( blocking scopeを有効にする)
    • +1(有効にすべき)
  • --harmony_modules (modulesを有効にする)
    • -1 (有効にしない)
  • --harmony_symbols (symbolsを有効にする private name としても知られる機能)
    • +1(有効にすべき)
  • --harmony_proxies (proxiesを有効にする)
    • -1
  • --harmony_collections (collections (sets, maps, and weak maps)を有効にする)
    • +1 (有効にするべき 既にimplementされてるものもあるが)
  • --harmony_observation (object observeを有効にする)
    • -1(有効にしない)
  • --harmony_generators (generatorsを有効にする)
  • --harmony_iteration (for-ofを有効にする)
    • -1(有効にしない)
  • --harmony_numeric_literals (numeric literals (0o77, 0b11)を有効にする)
    • +1(有効にすべき)
  • --harmony_strings (string拡張を有効にする)
    • +1(有効にすべき)
  • --harmony_arrays (arrays拡張を有効にする)
    • +1(有効にすべき)
  • --harmony_maths (math functionsを有効にする)
    • +1(有効にすべき)

もう一つ考えなきゃいけないこととして、今、nodeで使っているv8のバージョンが3.22でunstableなので、0.12までには3.23に上げたいと思っている、ただ、v8の3.24の開発も始まっていて、これを含めるまでの余裕が0.12のリリースまでにあるのかは分かっていない。

othiym23

いやーツール開発者から見ると有効にされてる機能ごとにテストしなきゃいけないの辛いわー。
悪夢のようなので、v8で有効になったら変更する今までのプランがいいわー。

domenic

いや、ちょっと見方を変えると、単に--harmonyを付けるよりもNode.jsにおいて安全な機能と安全じゃない機能が分けられて便利かもしれない。
これまでのES5とかでの対応を考えるとES6がちゃんと決まって、ちゃんと実装されるのって2018年とかになっちゃうし、少しずつでも有効にできるならいいかも。

jonathanong

koaメンテナからすると --harmony-generator だけでもデフォルトにしてくれないかな。
ユーザーに一々--harmony付けてくれっていうの面倒なんだよね。

trevnorris

個人的には以下の点でES6サポートは反対だな。

1. ES6を有効にするってことはv8でもやられていないようなテストをこっちで一緒にやっていく必要が有ると思ってる。
2. ES6を有効にするとcodeベースが厚くなる、もっとシンプルなものを提供したほうがユーザーのためだと思ってる。

2014/02/01 追記分

RushPL

harmony_collection は利用可能にするべきじゃないよ。
これを見てくれ、、

(new Set([1, 2, 3])).size
// =>0 firefoxでは3が返ってくるし、specも3だと記されてる。

domenic

そうそう。setのコンストラクタが未実装なんだよな。
まぁでもそれがCollectionで実装されてない唯一の項目だったはず。

mikeal

ちょっとずつ機能を追加していくのは互換性検証のために悪夢のような時間を使うことになるだろうし、それってPython 2.xのリリースみたいな状況を引き起こしかねないよね。v0.8の時の変更以上にインパクトを与えてしまうと思う。

準備が整ってからすべてを利用可能にして、これが"ES6の機能だ"というアナウンスを出したほうがモジュール開発者はES6の機能が追加されたことだけ互換性の検証すればいいから楽だと思う。

もちろん、harmony をproductionで使いたいというcrazyな開発者もいると思う。それ自体はすごくいいことで、僕らはcrazyな開発者も大切にしないといけない。そういう人たちのために harmony flagを用意している訳だしね。

ただし、コアチームが一番気を使わないといけないのはエコシステムの大多数の開発者が安定して運用できることと、unstableな機能をcrazyな開発者たちに使ってもらうことでコアのテストを手助けしてもらうことだと思うんだ。

domenic

これだけ言っておきたいんだけど、Python2/3と違ってEcmaScript5/6は互換性に最大限に注意してるよ。
ES6はES5のコードを壊すようなことはないはずだ。

一般的には、バージョンアップするのは勇気がいることだけど、EcmaScriptはそういう厳格に定義されたバージョンではなく、モジュール的に新しい機能が追加されていくようなモデルなんだ。だからバージョン番号にそんなに意味は無いんだ。
だからv8はObject.observeっていうES7で入るような機能をdirect proxiesっていうES6で入る機能よりも前に提供しようとしてるし。

だから準備が整ったかどうかを判断する責任を放棄したいのなら、v8がデフォルトにするまで待つ、っていうアプローチもいいと思うけど、
v8の開発者たちが急にharmonyデフォルトにするって言った時に、「こっちの準備が整ってないからちょっと待ってよ」みたいなことはするべきじゃないよね。じっくり準備するためにも少しずつでもいいから提供するべきだと思うんだ。

isaacs

> Python2/3と違ってEcmaScript5/6は互換性に最大限に注意してるよ。

これって、理想的にはそうだと思うんだけど、generatorやblockスコープを有効にして、collectionとかmoduleは有効にしないとしたら、Nodeのバージョンごとに動く機能と動かない機能が出てくるよね。それはそれで厳しい。

もし harmony オプション全体を有効にしたら効果的だろうとは思うけど、実装されてない機能があるとなると嫌なバグを踏むことになりそうだよね。「promiseの機能はあるけど、あれ、そういえば動いてないんだっけ」みたいなことになりかねない。

harmonyオプションに頼ることができるのであれば、 @bnoordhuis や @mikeal の意見に賛成で、 「v0.12からharmonyを始めます」と宣言すればいい。

symlinkの追加やargv[0]でチェックすることは一時的な問題に対してのアプローチに見える。node_hを作ったら将来的にnodeのharmonyが有効になった後も#!/usr/bin/env node_h のようなshebangが書かれたモジュールをサポートし続けなきゃいけなくなる。

harmonyオプションを全員に有効にするか、今の状況を続けるという苦渋の決断をするしかないと思う。

ついでに言うと、proxiesが利用可能になったら、node_contextify.ccをjsに変換できると信じている。

othiym23
@isaacs @domenic V8チームがES6を提供する準備が完了したと判断したらそのフラグはもはや不要になるだろう、そしたらマージしたらいいと思う。

でも今回言われてる実装状況がバラバラという問題があるならnodeのstable version (0.10, 0.12, 1.0) ではv8のバージョンもstableにした方がいいだろう。V8が3.24のpatchでES6を少しずつ小出しに実装していくなら、patchをアップデートしていくのは避けたい。

1.0にするなら安定させるべきで、これから実装していく言語のライブラリが依存しているのは厳しい。

TJ Fontaine:


このissueについて意見を寄せてくれてありがとう、いまはharmonyオプションに関しての変更はしないことにするよ。

議論の余地がまだまだたくさんあるような変更をこのリリース間近の段階で入れるのは遅すぎる。

0.12の後でこの類の話をするかもしれないが。

当分の間は、Nodeはv8がharmonyの機能を有効にするまでは有効にしないという決定を続けることにしよう。


翻訳適当なところもありますし、全部翻訳してないですが、流れは分かるかと思います。

まとめ

  • node v0.12でもharmonyオプションが有効にはなりません。
  • node_hというharmonyの機能をいくつか含んだ実行ファイルができるかも、という話はあったがまだまだ議論中。
  • nodeの0.12以降でまた蒸し返しがあるかもしれません。

いずれにせよ、今の段階では時期尚早ですね。

※ ちなみにissue openerである Bnoordhuisは 12月頃議論になった方ですが、元気にissueもpull reqも投げてます。