JavaScriptの人気の高まりは、今日では根本的に異なっているため、Web開発の表面を含むいくつかの変化をもたらしました。 JavaScriptをサーバーとブラウザーで実行することで、今日Webで実行できることは、数年前には想像が困難であったか、FlashやJavaなどのサンドボックス環境にカプセル化されています。
お問い合わせの前に Node.js 、スタック全体でJavaScriptを使用する利点について読みたいと思うかもしれません。これは、言語とデータ形式(JSON)を統合し、開発者リソースの最適な再利用を可能にします。これは特にNode.jsよりもJavaScriptの利点であるため、ここではあまり説明しません。ただし、ノードをスタックに組み込むことは重要な利点です。
Wikipediaが示唆しているように、「Node.jsは、ECMAScriptプログラミング言語に基づく(ただしこれに限定されない)サーバーレイヤー用のオープンソースのクロスプラットフォームランタイム環境であり、非同期で、イベント駆動型アーキテクチャに基づくデータのI / Oを備えています。 GoogleのV8エンジンで。」さらに、Node.jsの作成者であるRyan Dahlが、「Gmailなどのアプリに触発された」リアルタイムの埋め込みWebサイトを作成するように設定されたことは注目に値します。 Node.jsで、彼は開発者に、非ブロッキングのイベント駆動型I / Oパラダイムに取り組むためのツールを提供しました。
要求/応答プロトコルパラダイムに基づくステートレスプロトコルの20年後、私たちはついにリアルタイムWebアプリケーション、双方向接続を手に入れました。
一言で言えば、Node.jsは、Websocketを介したプッシュテクノロジーを採用したリアルタイムWebアプリケーションで輝いています。それについて何がそんなに革命的ですか?ステートレス要求/応答パラダイムに基づくステートレスWebサイトの20年以上の後に、クライアントとサーバーの両方が通信を開始してデータを自由に交換できるリアルタイムWebアプリケーション、双方向接続がついに完成しました。これは、顧客が常にコミュニケーションを開始する典型的なWeb応答パラダイムとは対照的です。また、すべてが標準ポート80で実行されているOpen Web Stack(HTML、CSS、およびJS)に基づいています。
何年もの間、FlashおよびJavaアプレットの形式でこの形式を使用してきたと言えますが、実際には、これらは、クライアントに配信されるトランスポートプロトコルとしてWebを使用する単なるサンドボックス環境でした。また、これらは単独で実行され、多くの場合、非標準のポートを介して動作します。これには、使用するための追加の要件がある場合があります。
Node.jsは、そのすべての利点とともに、独自の利点に依存している多くの著名な企業のテクノロジースタックで重要な役割を果たしています。
この記事では、これらの利点がどのように得られるかだけでなく、Node.jsを使用する理由と、いくつかの古典的なWebアプリケーションモデルを例として使用しない理由についても説明します。
Node.jsの主なアイデア:非ブロッキングのイベント駆動型I / Oを使用し、分散デバイスで実行されているアプリケーションの大量のリアルタイムデータ使用の表面で軽量かつ効率的に維持します。
すごいですよね?
それが本当に意味するのは、Node.jsはWeb開発の世界を支配する新しいプラットフォームではないということです。むしろ、それは特定のニーズを満たすプラットフォームです。
そして、この理解は絶対に不可欠です。 CPUを集中的に使用する操作にNode.jsを使用することは絶対に避けてください。実際、重い計算に使用すると、ほとんどすべての利点が無効になります。 Nodeが本当に優れているのは、ネットワークアプリケーションの高速でスケーラブルな構築です。これは、高性能で多数の同時接続を処理できるため、高いスケーラビリティに相当します。
それが内部でどのように機能するかは非常に興味深いものです。各接続(リクエスト)が新しいスレッドを生成し、システムRAMを取り戻し、最終的に使用可能なRAMの量をいっぱいにする従来のウェブサービス技術と比較して、Node.jsは単一のスレッドで動作し、コールブロッキングI / Oを使用しません、数万の同時接続をサポートできるようにします(ループの場合に保持されます)。
簡単な計算:各スレッドに2 MBのメモリが伴う可能性があると仮定すると、8 GBのRAMを備えたシステム内で実行されるため、コンテキスト切り替えのコストに加えて、理論上最大4,000の同時接続が可能になります。スレッド。これは、従来のWebサービス技術でよく扱われるシナリオです。それをすべて回避すると、Node.jsは100万を超える同時接続のスケーラビリティレベルに達します( 概念実証として )。
もちろん、すべてのクライアント要求間で単一のスレッドを共有する機能があり、Node.jsアプリケーションの作成に失敗する可能性があります。まず第一に、重い計算は停止し、そのような計算が完了するまでブロックされる着信要求など、すべてのクライアントに問題を引き起こす可能性があります(これについては後で詳しく説明します)。次に、開発者は、コア(一番上のもの)にバブリング例外を許可しないように非常に注意する必要があります。これにより、Node.jsインスタンスがクラッシュします( プログラムを効果的にブロックする )。
例外を回避するために使用される手法は、(他の環境のようにエラーをプルするのではなく)パラメーター呼び出しとしてエラーを呼び出しに渡します。例外が発生した場合でも、ノードプロセスを監視し、緊急時に必要な回復を実行するために使用できるツールがいくつかあります(ただし、ユーザーセッションを回復することはできません)。最も一般的な緊急事態は、Foreverモジュール、または新興の外部システムツールとモニターを使用した別のアプローチです。
Node.jsについて話すとき、絶対に省略してはならないことの1つは、すべてのNode.jsインストールにデフォルトで付属しているNPMツールを使用してパッケージ管理サポートに統合することです。 NPMモジュールの考え方はRubyGemsと非常によく似ています:バージョンと依存関係の管理を備えたオンラインリポジトリからの簡単なインストールを通じて公開されている再利用可能なコンポーネントのセットです。
モジュールパッケージの完全なリストは、NPM WebサイトHttps://npmjs.org/にあるか、Node.jsとともに自動的にインストールされるNPMCLIツールを使用してアクセスできます。このモジュールは誰でも利用できるエコシステムであり、NPMリポジトリに含まれる独自のモジュールを誰でも公開できます。 NPMの簡単な紹介(少し古いですが、まだ有効です)は次の場所にあります。 http://howtonode.org/introduction-to-npm 。
今日最も人気のあるもののいくつかはNPMモジュールです:
anglejsから始める方法
エクスプレス --Express.jsは、Node.jsのWeb開発フレームワークに触発され、今日のほとんどのNode.jsアプリケーションの事実上の標準です。
接続する --Connectは、Node.js用の拡張可能なHTTPサーバーフレームワークであり、ミドルウェアと呼ばれるプラグインの高性能コレクションを提供します。表現するための基盤として機能します。
socket.io Y sockjs -今日最も一般的な2つのWebSocketコンポーネントのサーバーコンポーネント。
翡翠 -Express.jsの欠陥であるHAMLに触発された最も人気のあるテンプレートエンジンの1つ。
モンゴ Y mongojs --Node.jsのMongoDBオブジェクトデータベースにAPIを提供するmongoDBラッパー。
繰り返す --Redisクライアントライブラリ。
コーヒースクリプト -開発者がコーヒーを使ってNode.jsプログラムを作成できるようにするCoffeeScriptコンパイラ。
アンダースコア (( lodash 、 怠惰 )-Node.jsで使用するためにパッケージ化されたJavaScriptの最も人気のあるユーティリティライブラリと、わずかに異なるアプリケーションアプローチを採用することでパフォーマンスの向上を約束する2つの対応ライブラリ。
永遠に -特定のノードスクリプトが継続的に実行されるようにするための、おそらく最も一般的なユーティリティ。 Node.jsプロセスを本番環境で維持し、予期しないクラッシュが発生した場合に備えます。
デビットカードをハックする方法
リストは無限大です。誰もが利用できる本当に便利なパッケージがたくさんあります(ここでスキップしたものには違和感はありません)。
これは、最も一般的なリアルタイムのマルチユーザーアプリケーションです。 IRC(当時)から、非標準ポートで回転する多くの独自のオープンプロトコルを介して、標準ポート80で実行されているWebSocketを使用してNode.jsのすべてをインストルメント化する機能を備えています。
チャットアプリはNode.jsに最適です。軽量でデータ集約型(ただしスループット/コンピューティングは低い)のトラフィックであり、分散デバイスで動作するアプリです。単純すぎるため、学習の優れたユースケースでもありますが、同時に、一般的なNode.jsアプリケーションで使用できるほとんどのツールをカバーしています。
それがどのように機能するかを説明しようとします。
最も単純な例では、Webサイトに1つのチャットルームがあり、1人または複数の人とメッセージを交換できます。たとえば、サイトに3人のユーザーが全員メッセージボードに接続しているとします。
サーバー側には、2つのことを実装する単純なExpress.jsがあります。1)メッセージボードを含むWebページを提供するリクエストハンドラー「/」と、入力から新しいメッセージを初期化する「送信」ボタンを取得します。2 )WebSocketクライアントによって発行されたメッセージをリッスンするWebSocketサーバー。
クライアントには、いくつかのハンドラーを含むHTMLページがあります。1つは入力メッセージを取得してWebSocketに送信する[送信]ボタンクリックイベント用で、もう1つは新しいクライアントからの着信メッセージをリッスンします。websockets (つまり、他のユーザーから送信されたメッセージで、サーバーがクライアントに表示するようにします)。
クライアントの1つがメッセージを送信すると、次のようになります。
ブラウザは、入力フィールドの値(つまりメッセージテキスト)を取得するJavaScriptハンドラーを介して[送信]ボタンのクリックをキャッチし、サーバーに接続されたWebSocketクライアント(Webページの初期化で初期化)を使用してWebSocketメッセージを発行します。
WebSocket接続のサーバーコンポーネントはメッセージを受信し、ブロードキャスト方式を使用して接続されている他のすべてのクライアントにメッセージを転送します。
すべてのクライアントは、Webページ内で実行されるwebsocketsクライアントコンポーネントを介してプッシュメッセージとしてメッセージを受信します。次に、新しいメッセージをボードに追加する代わりに、メッセージのコンテンツを収集してWebページを更新します。
これは最も簡単な例です。より堅牢なソリューションとして、Redisストアに基づく単純なキャッシュを使用できます。または、より高度なソリューションでも、クライアントへのメッセージのルーティングを管理するメッセージキューと、一時的な接続損失をカバーしたり、切断中に登録済みクライアントのメッセージを保存したりできる、より堅牢な配信メカニズムがあります。ただし、行った拡張に関係なく、Node.jsは、イベントへの対応、多数の同時接続の処理、ユーザーエクスペリエンスの流動性の維持という同じ基本原則の下で動作します。
Node.jsはリアルタイムアプリケーションの中で本当に際立っていますが、DBオブジェクト(MongoDBなど)からデータを公開するのに自然に適合します。 JSONデータストレージにより、Node.jsはインピーダンスの不一致やデータ変換なしで機能できます。
たとえば、Railsを使用している場合、JSONデータをバイナリモデルに変換し、データがbackbone.js、anglesなど、または通常のjQuery AJAXによって消費されるときに、JSON overHTTPとして再度公開する必要があります。呼び出します。 Node.jsを使用すると、クライアントが使用できるように、RESTAPIを使用してJSONオブジェクトを簡単に公開できます。また、データベースからの読み取りまたは書き込み時に、JSONと他のものとの間の変換について心配する必要はありません(MongoDBを使用している場合)。結論として、クライアント、サーバー、およびデータベース全体で一貫したデータシリアル化形式を使用することにより、複数の変換の必要性を回避できます。
大量の同時データを受信している場合、データベースが詰まる可能性があります。上記のように、Node.jsは同時に簡単に同時接続を処理できます。ただし、データベースへのアクセスはブロック操作(この場合)であるため、問題が発生します。解決策は、データが実際のデータベースに書き込まれる前に、クライアントの動作を認識することです。
このアプローチでは、システムは高負荷下でも感度を維持します。これは、クライアントが正しいデータ書き込みを強力に確認する必要がない場合に特に役立ちます。典型的な例としては、ユーザー追跡データのログ記録または書き込み、後で使用されるまで使用されないバッチ処理、および最終的な一貫性(非常に頻繁に)で即座に反映される必要のない操作(Facebookのいいねカウントの更新など)があります。 NoSQLの世界で使用されている)は許容されます。
データは、ある種のキャッシュまたはメッセージキュー(インフラストラクチャ、 RabbitMQ 、 ZeroMQ )そして、そのようなタスクのためのより良いパフォーマンスプラットフォームで書かれた、バッチ、計算、または処理集約型のバックエンドサービスで書かれた別のプロセスによって要約されます。同様の動作を他の言語/フレームワークで実装できますが、パフォーマンスを維持するために同じハードウェアまたは同じ高さで実装することはできません。
結論:Nodeを使用すると、書き込まれたデータベースを脇に置いて後で処理し、成功したかのように進めることができます。
従来のWebプラットフォームでは、HTTP要求と応答は分離されたイベントとして扱われます。実際、それらは本当に一般的です。この観察結果をNode.jsで使用して、いくつかの優れた機能を構築できます。たとえば、データはストリームを介して入力されるため、アップロード中にファイルを処理することができ、ファッションラインで処理することができます。これは、異なるデータソース間のプロキシとして、オーディオまたはビデオエンコーディングに対してリアルタイムで実行できます(次のセクションを参照)。
ノードPROXY.jsは、非ブロッキングモードで多数の同時接続を処理できるプロキシサーバーとして使用されます。これは、異なる応答時間で異なるサービスをプロキシする場合、またはさまざまな起点からデータを収集する場合に特に役立ちます。
例:サードパーティのリソースと通信したり、さまざまなソースからデータを抽出したり、画像や動画などのアセットをサードパーティのクラウドサービスに保存したりするサーバーアプリケーションについて考えてみます。
専用のプロキシサーバーがありますが、プロキシサーバーのインフラストラクチャが存在しない場合、またはローカル開発用のソリューションが必要な場合は、代わりにNodeを使用すると便利です。つまり、プロキシ/スタブAPIリクエストなどのアセット用にNode.js開発サーバーを使用してクライアント側アプリケーションを構築できますが、本番環境では、専用のプロキシサービス(nginx、HAProxyなど)とのやり取りを処理します。 )。
アプリケーションレベルに戻りましょう。デスクトップソフトウェアが優勢であるが、リアルタイムWebに簡単に置き換えることができる別の例は、商用ソフトウェアエージェントソリューションです。株価の追跡、技術的な計算と分析の実行、チャートや図の作成に使用されます。
リアルタイム切り替えは、ブローカーがワークステーションや職場を簡単に切り替えることができるWebベースのソリューションです。すぐに私たちはフロリダ、イビサ...またはバリのビーチでそれらを見始めることができました。
Node-con-web-socketsが完全に適合するもう1つの一般的な使用例は、これです。Webサイトの訪問者を追跡し、それらのインタラクションをリアルタイムで表示します。 (興味があれば、このアイデアはすでにColibríによって作成されています)。
ユーザーからリアルタイムで統計を収集したり、訪問者が目標到達プロセスの特定のポイントに到達したときに通信チャネルを開いて訪問者との選択的なインタラクションを導入することで、次のレベルに上がることもできます。 (興味があれば、このアイデアはすでにCANDDiによって作成されています。)
訪問者がリアルタイムで何をしているかを知っていれば、ビジネスがどのように改善されるか想像してみてください。あなたが彼らの相互作用を視覚化することができれば。リアルタイムで、Node.jsから2つの方法を利用できるようになりました。
次に、システム監視パネルで、インフラストラクチャの観点を理解しましょう。たとえば、ユーザーに監視サービス(GitHubページなど)を提供したいSaaSプロバイダーを想像してみてください。 Node.js-loopイベントを使用すると、状態サービスを非同期でチェックし、Websocketを使用してクライアントにデータを送信する強力なWebベースのダッシュボードを作成できます。
このテクノロジーを使用して、社内(社内)と米国の公共サービスの両方をライブでリアルタイムに報告できます。このアイデアをもう少し推し進めて、通信事業者、クラウド/ネットワーク/ホスティングサービスプロバイダー、または一部の金融機関のアプリケーションを監視するネットワークオペレーションセンター(NOC)を想像してみてください。これらはすべて、Node.jsでサポートされているオープンWebスタックで実行されます。およびJavaおよび/またはJavaアプレットの代わりにWebsockets。
注:ノードでハードリアルタイムシステム(つまり、一貫した応答時間を必要とするシステム)を構築しようとしないでください。この種のアプリケーションには、おそらくアーランの方が適しています。
Express.jsを使用したNode.jsを使用して、サーバー上に従来のWebアプリケーションを作成することもできます。ただし、可能な限り、このNode.jsの要求/応答パラダイムはHTMLを持ち歩くため、最も一般的なユースケースではありません。このアプローチには賛成と反対の議論があります。考慮すべきいくつかの事実は次のとおりです。
アプリケーションがCPUを集中的に使用しない場合は、MongoDB DBなどのJSONストレージオブジェクトを使用している場合でも、データベースレベルでもJavascriptを上から下にビルドできます。これにより、開発(採用を含む)が大幅に促進されます。
クローラーは完全なHTML応答を受け取ります。これは、はるかにSEOに適しています。たとえば、単一のページまたはWebsocketsアプリがNode.js上で実行されます。
計算集約型のCPUはNode.jsの応答性をブロックするため、スレッドリグがより良いアプローチです。または、カウント[*]をスケーリングしてみることもできます。
リレーショナルデータベースでNode.jsを使用することは、依然として非常に苦痛です(詳細については以下をお読みください)。関係演算を実行しようとしている場合は、Rails、Django、ASP.NETMVCなどの他の環境を選択してください。
たとえば、Ruby on Railsに対してNode.jsとExpress.jsを比較すると、リレーショナルデータアクセスに関しては後者を支持する明確な決定があります。Node.js用のツールを備えたリレーショナルDBはまだ初期の段階です。ステージ;それはかなり時期尚早であり、したがって、一緒に作業するのはそれほど快適ではありません。一方、Railsは、データベーススキーマおよび他のGemsからの移行サポートツール(二重の意味を持つ)とともに、すぐに使用できるアクセス構成データを自動的に提供します。 Railsとそれに対応するフレームワークは成熟しており、Active Record Data Mapperが、純粋なJavaScriptで複製しようとすると見逃してしまうデータアクセスの実装を収集することを証明しています。[*]
それでも、JSにずっととどまりたいと思っている場合は、Sequelize ORMとNode2はまだ未成熟ですが、最終的には他のプログラミング言語に追いつく可能性があるため、注意してください。
[]は可能であり、Nodeをフロントエンドとしてのみ使用し、Railsのバックエンドを維持してリレーショナルデータベースに簡単にアクセスできることも珍しくありません。
ヘビーコンピューティングに関しては、Node.jsは最適なプラットフォームではありません。 Node.jsでフィボナッチ計算サーバーを構築することは絶対に避けてください。一般に、CPUを集中的に使用する操作は、パフォーマンス上の利点をすべて無効にし、スレッドからの着信要求をブロックします。
上記のように、Node.jsはシングルスレッドであり、単一のCPUコアを使用します。マルチコアサーバーに同時実行性を追加する場合、クラスターモジュールの形式で基本ノードによって実行される作業がいくつかあります[参照: http://nodejs.org/api/cluster.html ]。また、nginxを介してリバースプロキシの背後でNode.jsサーバーの複数のインスタンスを非常に簡単に実行できます。
オプションの価格設定方法
バンドルを使用すると、より適切な環境内で記述されたバックグラウンドを処理するためにすべての重い計算をオフロードし、メッセージキューを介してRabbitMQとして通信させる必要があります。
バックグラウンド処理は最初は同じサーバーで実行される場合がありますが、このアプローチには非常に高いスケーラビリティの可能性があります。バックグラウンド処理サービスは、さまざまなWebサーバーの負荷を構成する必要なしに、サーバーとは独立してワーカーに簡単に分散できます。
もちろん、他のプラットフォームでも同じアプローチを使用しますが、Node.jsを使用すると、各リクエストが小さなタスクであり、非常に迅速かつ効率的に処理されるため、これまでに説明した高いリクエストを実現できます。
Node.jsについては、その目標と野心から始まり、スイートスポットと落とし穴で終わる実用的な理論から説明しました。人々がNodeに問題を抱えているとき、彼らはほとんどの場合、ブロック操作がすべての悪の根源であるという事実を推測します。ノードの乱用の99%は、直接的な結果として発生します。
注意:Node.jsは、計算スケーリングの問題を解決するために作成されたものではありません。これは、I / Oスケーリングの問題を解決するために作成されました。これは非常にうまく機能します。
Node.jsを使用する理由ユースケースにCPUを集中的に使用する操作やブロッキングリソースへのアクセスが含まれていない場合は、Node.jsの利点を活用して、高速でスケーラブルなネットワークアプリケーションを楽しむことができます。リアルタイムでウェブへようこそ。
トミスラフ・カパン 、クロアチア
トミスラヴ はソフトウェアエンジニア、技術コンサルタント、アーキテクトであり、10年以上の経験があります。彼はFull-Slackを専門としており、JavaScriptとNode.jrに非常に精通しています。 C#、Java、Rubyでの作業経験があります。彼は、開発プロジェクトでのコラボレーションが大好きなアジャイルかんばんの実践者です。