SmooshGate に関するよくある質問

いったい何が起きたんだ?

JavaScript のプロポーザル Array.prototype.flattenという言語機能は ウェブ非対応。Firefox Nightly で機能をリリースしたことで、少なくとも 1 つの人気ウェブサイトが発生した ありません。問題のあるコードは広く普及している MooTools の一部であることから 多数のウェブサイトが影響を受ける可能性があります。(MooTools では、 2018 年には新しいウェブサイトにあまり使われていませんでした 制作されたウェブサイトには依然として存在しています)。

提案書では、次のように flattensmoosh に名前変更することを冗談交じりに提案していました。 互換性の問題を回避できますジョークが明確ではなかった 人々は新しい名前がすでに名前に付けられていたと 事態が急速にエスカレートしました

Array.prototype.flatten の機能

Array.prototype.flat(当初は Array.prototype.flatten として提案) 指定されたdepthまで配列を再帰的にフラット化します。これはデフォルトで 宛先: 1

// Flatten one level:
const array = [1, [2, [3]]];
array.flat();
// → [1, 2, [3]]

// Flatten recursively until the array contains no more nested arrays:
array.flat(Infinity);
// → [1, 2, 3]

同じ提案に Array.prototype.flatMap が含まれています。 Array.prototype.map と異なります。ただし、結果を新しい配列にフラット化します。

[2, 3, 4].flatMap((x) => [x, x * 2]);
// → [2, 4, 3, 6, 4, 8]

この問題の原因となっているのは、MooTools のどのような行為ですか?

MooTools では、Array.prototype.flatten の非標準バージョンが独自に定義されています。

Array.prototype.flatten = /* non-standard implementation */;

MooTools の flatten の実装が、提案された標準と異なります。 しかし、これは問題ではありません。ブラウザのリリース時期 Array.prototype.flatten は、MooTools でそのネイティブ 説明します。これにより、MooTools の動作に依存するコードが ネイティブの flatten を使用できるかどうかにかかわらず、意図したとおりに動作する。 順調です。

しかし残念なことに、その後は別のことが起こります。MooTools は、 Elements.prototype へのカスタム配列メソッド(Elements は MooTools 固有の API):

for (var key in Array.prototype) {
  Elements.prototype[key] = Array.prototype[key];
}

for-in は、「enumerable」プロパティを反復処理します。 Array.prototype.sort などのネイティブ メソッドですが、 定期的に割り当てられる Array.prototype.foo = whatever などのプロパティ。でも - これはキッカーです。列挙不可能なプロパティを上書きした場合( Array.prototype.sort = whatever の場合、列挙不可のままとなります。

現在、Array.prototype.flatten = mooToolsFlattenImplementation によって作成される 列挙可能な flatten プロパティなので、後で Elements にコピーする。しかし、 ブラウザにはネイティブ バージョンの flatten が搭載されているため、列挙不可になり、 Elements にコピーされませんMooTools の Elements.prototype.flatten が破損している。

ネイティブの Array.prototype.flatten を次のように変更しているようですが、 enumerable の場合、問題が修正されますが、 サポートしています。forinの反復処理を必要とするすべてのウェブサイト 配列(これはよくない手法ですが、実際に起こります)は、 flatten プロパティの追加のループ反復処理。

ここでの大きな根本的な問題は、組み込みオブジェクトの変更です。拡張 最近ではネイティブ プロトタイプが好ましくないとされています。これは、 他のライブラリやサードパーティのコードとはうまく連携しません。変更しない 削除することはできません。

既存の名前をそのまま維持して、ウェブを破滅に追いやればいいのではないでしょうか?

1996 年、CSS が普及する前から、「HTML5」が Space Jam のウェブサイトが公開されました。現在でもウェブサイトは稼働している 22 年前と同じです

なぜでしょうか?誰かがそのウェブサイトをずっと維持していたのか、 ブラウザ ベンダーが新機能をリリースするたびに更新しますか。

結局のところ、「ウェブを壊さない」ことが設計の最優先事項 HTML、CSS、JavaScript のほか、 ウェブ。新しいブラウザ機能のリリースに伴い、既存のウェブサイトが停止する場合 すべての人に悪影響を及ぼします。

  • 影響を受けたウェブサイトの訪問者が突然ユーザーエクスペリエンスに悪影響を及ぼした場合。
  • ウェブサイトの所有者は完璧に機能するウェブサイトから 何も変更せずに機能しないもの。
  • 新機能をリリースするブラウザ ベンダーは、ユーザーが原因でマーケット シェアを失う 「ブラウザ X で動作します」と表示された後にブラウザを切り替える。
  • 互換性の問題が判明した場合、他のブラウザ ベンダーはリリースを拒否します。 できます。機能の仕様が現実と一致しない(「何も架空の作品」) 標準化プロセスに悪影響を及ぼします

たしかに振り返ってみると、MooTools の行動は間違っていたが、ウェブが壊れてしまった ペナルティはありませんこれらのユーザーは 説明します。または、別の解決策を見つけてユーザーが続行することもできます。 必要ありません。選択は簡単です。

ウェブ プラットフォームから不適切な API を削除できないということでしょうか?

場合によって変わります。まれに、不適切な機能がウェブから削除されることがあります。たとえ考えれば ある特徴を削除できるかどうかを確認するのは、非常に厄介な作業です。 ウェブページ数を定量化するためには 広範なテレメトリーが必要になります 動作が変わります。ただし、この機能が十分に安全ではない場合、 ほとんど使用されていない場合、この処理は可能です。

<applet><keygen>showModalDialog() はすべて ウェブ プラットフォームから正常に削除された不正な API の例

MooTools を修正するのはどうしてですか?

組み込みオブジェクトを拡張しないように MooTools にパッチを適用すると、 考えていますしかし、それで目の前の問題が解決するわけではありません。MooTools が パッチ適用済みのバージョンをリリースするためには、そのバージョンを使用しているすべての既存ウェブサイトで、 互換性の問題がなくなります。

MooTools のコピーを更新できないのであれば、

MooTools でパッチがリリースされ、すべての 翌日には魔法のように更新されるようになります。問題は解決しました。 いい?!

これは非現実的です。たとえ誰かがなんらかの形で 影響を受けるすべてのウェブサイトにアクセスし、 ウェブサイトの所有者と連絡を取り合って 更新を行うよう全員を説得します(場合によっては コードベース全体など)では、プロセス全体はせいぜい数年かかるでしょう。

このようなウェブサイトの多くは古く、管理されていない可能性が高いことに留意してください。 メンテナンス担当者がまだ近くにいても、 高度なスキルを持つウェブ デベロッパーになります。すべての人が とウェブの互換性の問題で 8 歳の子どものウェブサイトを何度も変更したとします。

TC39 のプロセスの仕組み

TC39 は、JavaScript 言語の進化を担当する委員会で、 ECMAScript 規格に準拠しています。

#SmooshGate では、「TC39 が flatten の名前を 「smoosh」と書かれているのに、このジョークは外部にあまり知られていないジョークでした。 プロポーザル名の変更などの重要な決定は、慎重に検討し、 1 人で行われることになり、1 人で GitHub のコメント。

TC39 は、機能提案の明確なステージング プロセスを定めています。 ECMAScript の提案およびそれらに対する大幅な変更( 名前の変更など)について、TC39 ミーティングで議論され、承認を受ける必要がある 委員会全体で目を離さずに済みますケースが Array.prototype.flatten 様、この提案はすでに複数回行われています ステージ 3 までのすべてのステージで、特徴が ウェブブラウザに実装できます。追加の仕様書は、 問題を簡単に解決できますこの場合最も重要なのは リリースしようとしたに寄せられたフィードバック ウェブを壊す可能性があります。このような予測が困難な問題が TC39 のプロセスは、ブラウザが機能をリリースした後に終わるわけではありません。

TC39 はコンセンサスに基づいて運営されており、すなわち、委員会が新しい契約について合意する必要がある できます。smoosh が真面目な提案だったとはいえ、おそらく 委員会のメンバーはこれに異議を唱えて compact または chain

flatten から smoosh への名前変更は(冗談ではありませんでしたが) TC39 ミーティングでは話し合われたことがありません。そのため、TC39 の このトピックは現在不明です。1 人が代理で発言できない 次回の会議で合意に達するまで、すべての TC39 が

通常、TC39 ミーティングには多様性に富んだ人々が参加します。 プログラミング言語デザインの経験、 ブラウザや JavaScript エンジンを使用するものがあり、 JavaScript のデベロッパー コミュニティを表すために役立ちます。

SmooshGate は最終的にどのように解決されたのですか?

2018 年 5 月の TC39 会議の際、#SmooshGate は、flatten の名前を flat に変更することで正式に解決されました。

Array.prototype.flatArray.prototype.flatMap は V8 v6.9 でリリースされ、 Chrome 69。