1. ホーム
  2. javascript

[解決済み] インブラウザのJavaScriptにNodeスタイルのrequireを?[クローズド]

2023-02-13 16:44:36

質問

Nodeのような柔軟性/モジュール性/使いやすさを提供するブラウザ内javascriptのためのライブラリはありますか? require ?

より詳細な説明をするために、理由 require が優れているのは、それが

  1. 他の場所からコードを動的に読み込むことができます (これは、HTML 内にすべてのコードをリンクするよりも、スタイル的に優れていると私は考えています)。
  2. モジュールを構築するための一貫したインターフェイスを提供する
  3. モジュールが他のモジュールに依存しやすくなります (例えば、jQuery を必要とする API を書いて、その API で jQuery.ajax()
  4. ロードされた javascript は スコープ付き でロードできることを意味します。 var dsp = require("dsp.js"); で読み込むと dsp.FFT にアクセスできるようになり、私のローカルの var FFT

私はまだ、これを効果的に行うライブラリを見つけたことがありません。 私が使いがちな回避策は

  • coffeescript-concat -- 他のjsをrequireするのは簡単ですが、コンパイルが必要なので、高速な開発(APIのインテスト構築など)にはあまり向いていません。

  • RequireJS -- これは人気があり、簡単で、1-3を解決してくれますが、スコープがないのは本当に致命的です(確か head.js もスコープがない点で似ていると思うが、私は使う機会がない。 同様に LABjs は読み込むことができ .wait() は依存性の問題を解決してくれますが、それでもスコープがありません)

私が知る限り、javascript の動的および/または非同期ロードのための多くのソリューションがあるように見えますが、それらは HTML から js をロードするだけの場合と同じスコープの問題を持つ傾向があります。 何よりも、グローバル名前空間をまったく汚染しない javascript をロードする方法が欲しいのですが、それでも (node の require がそうであるように) ライブラリをロードして使用することは可能です。

2020年最新版。 モジュール はES6で標準化され、2020年半ば現在、ネイティブにサポートされている ほとんどのブラウザで . モジュールは同期と非同期(Promiseを使用)の両方の読み込みをサポートしています。私の現在の推奨は、ほとんどの新しいプロジェクトはES6モジュールを使用し、レガシーブラウザのために単一のJSファイルにフォールバックするトランスパイラを使用することです。

一般的な原則として、今日の帯域幅は、私が最初にこの質問をしたときよりもはるかに広いのが普通です。したがって、実際には、ES6 モジュールで常にトランスパイラーを使用し、ネットワークよりもコードの効率に努力を集中させることを合理的に選択することができます。

PREVIOUS EDIT (またはES6モジュールが好きでない場合)。 これを書いてからというもの、私は広範囲に渡って RequireJS (を使うようになりました(今ではもっと明確なドキュメントがあります)。RequireJS は本当に正しい選択だったと私は思っています。私のように迷っている人のために、どのような仕組みになっているのかを明らかにしたいと思います。

を使うことができます。 require を日常の開発で使うことができます。モジュールは関数(通常はオブジェクトや関数)が返すものであれば何でもよく、パラメータとしてスコープが設定されています。また、デプロイメント用にプロジェクトを一つのファイルにコンパイルするには r.js を使うこともできます (実際にはこの方がほとんど常に高速ですが require はスクリプトを並行してロードすることができます)。

RequireJSとbrowserify(tjamesonが提案したクールなプロジェクト)のようなノードスタイルのRequireとの主な違いは、モジュールの設計と要求のされ方です。

  • RequireJSはAMD(Async Module Definition)を採用しています。AMDでは require は、ロードするモジュール(javascript ファイル)のリストとコールバック関数を受け取ります。各モジュールを読み込んだら、各モジュールをコールバックのパラメータとしてコールバックを呼び出します。したがって、これは真に非同期であり、したがってウェブによく適しています。
  • NodeはCommonJSを使用しています。CommonJSでは require はモジュールをロードし、それをオブジェクトとして返すブロッキングコールです。これは、ファイルがファイルシステムから読み込まれるため、Nodeでは十分に高速に動作しますが、同期的にファイルを読み込むとはるかに時間がかかるため、Webではうまく動作しません。

実際には、多くの開発者はAMDを見る前にNode(したがってCommonJS)を使ったことがあります。さらに、多くのライブラリ/モジュールが CommonJS 用に書かれています (たとえば、"Communication" のように exports オブジェクトに追加することで)CommonJS向けに書かれたものが多く、AMD向けには書かれていません(モジュールを define 関数からモジュールを返すことによって)。したがって、NodeからWebに転向した開発者の多くは、Web上でCommonJSライブラリを使用したいと考えています。これは <script> タグからの読み込みはブロックされるからです。browserifyのようなソリューションは、CommonJS(Node)モジュールを取り、それらをラップして、scriptタグでそれらを含めることができるようにします。

したがって、もしあなたがウェブ用の独自のマルチファイルプロジェクトを開発しているのであれば、私はRequireJSを強くお勧めします。最近、RequireJSでは、基本的にCommonJSの構文を使用できるようになったので、この区別はあまり重要ではなくなりました。さらに、RequireJSは、NodeでAMDモジュールをロードするために使用することができます(ただし、私は node-amd-loader ).

どのように解決するのですか?

チェックアウト エンダー . これは多くのことを行っています。

また ブラウザ化 はなかなかいい感じです。私が使っているのは require-kiss ¹で、うまくいきます。 おそらく他にもあると思います。

RequireJSはどうでしょう。nodeのと同じではないだけです。他の場所からの読み込みで問題が発生するかもしれませんが、うまくいくかもしれません。呼び出せるようなprovideメソッドとかがあれば。

TL;DR - browserifyかrequire-kissをお勧めします。


更新しました。

1: require-kiss はもう死んでしまったので、作者はそれを削除しました。その後、私は問題なくRequireJSを使用しています。require-kissの作者は次のように書いています。 pakmanager パックマン . 完全な開示、私は開発者と働いています。

個人的には、RequireJSの方が好きです。デバッグがはるかに簡単で(開発では別々のファイルを持ち、本番では単一のデプロイされたファイルを持つことができます)、堅実なquot;standard"に基づいて構築されています。