27

— Redis DBからデータ(50アイテム)を取得してローカルホストにスローするシンプルなアプリを作成しました。私はApacheBench(c = 100、n = 50000)を実行し、デュアルコアT2080 @ 1.73GHz(私の6年間のラップトップ)で半ばまともな150リクエスト/秒を取得していますが、procの使用法は非常に残念です表示: ここに画像の説明を入力してください

使用されるコアは1つだけで、これはNodeの設計によるものですが、Node.jsクラスターを使用できれば、リクエスト/秒をほぼ2倍の約300に、おそらくそれ以上に増やすことができると思います。私はかなりいじくり回しましたが、以下にリストされている私のアプリで使用するためにここに与えられたコードを置く方法を理解することができませんでした:

var 
    express = require( 'express' ),
    app     = express.createServer(),
    redis   = require( 'redis' ).createClient();

app.configure( function() {
    app.set( 'view options', { layout: false } );
    app.set( 'view engine', 'jade' );
    app.set( 'views', __dirname + '/views' );
    app.use( express.bodyParser() );
} );

function log( what ) { console.log( what ); }

app.get( '/', function( req, res ) {
    redis.lrange( 'items', 0, 50, function( err, items ) {
            if( err ) { log( err ); } else {
                res.render( 'index', { items: items } );
            }
    });
});

app.listen( 8080 );

また、このアプリはI / Oを集中的に使用することを強調したいと思います(CPUを集中的に使用しないため、クラスターよりもスレッドアゴーゴーのようなものが適しています)。

これを理解するのにいくつかの助けが欲しいです。

4

1 に答える 1

34

実際、ワークロードは実際にはI / Oバウンドではありません。翡翠ベースの動的ページ生成のコストのため、CPUバウンドです。翡翠テンプレートの複雑さは推測できませんが、単純なテンプレートを使用しても、HTMLページの生成にはコストがかかります。

私のテストでは、このテンプレートを使用しました。

html(lang="en")
  head
    title Example
  body
    h1 Jade - node template engine
    #container
      ul#users
        each user in items
          li User:#{user}

Redisのitemsキーに100個のダミー文字列を追加しました。

私のボックスでは、node.js CPUが100%の場合に475 req / sを取得します(これは、このデュアルコアボックスのCPU消費量が50%であることを意味します)。置き換えましょう:

res.render( 'index', { items: items } );

に:

res.send( '<html lang="en"><head><title>Example</title></head><body><h1>Jade - node template engine</h1><div id="container"><ul id="users"><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li><li>User:NOTHING</li></ul></div></body></html>' );

現在、ベンチマークの結果は2700 req/sに近くなっています。したがって、ボトルネックは明らかにHTMLページのフォーマットに起因します。

この状況でクラスターパッケージを使用することは良い考えであり、それは簡単です。コードは次のように変更できます。

var cluster = require('cluster')

if ( cluster.isMaster ) {
  for ( var i=0; i<2; ++i )
    cluster.fork();
} else {
  var
      express = require( 'express' ),
      app     = express.createServer(),
      redis   = require( 'redis' ).createClient();

  app.configure( function() {
      app.set( 'view options', { layout: false } );
      app.set( 'view engine', 'jade' );
      app.set( 'views', __dirname + '/views' );
      app.use( express.bodyParser() );
  });

  function log( what ) { console.log( what ); }

  app.get( '/', function( req, res ) {
      redis.lrange( 'items', 0, 50, function( err, items ) {
            if( err ) { log( err ); } else {
              res.render( 'index', { items: items } );
            }
      });
  });

  app.listen( 8080 );
}

これで、ベンチマークの結果は750 req / sに近くなり、CPU消費量は100%になります(最初の475 req / sと比較されます)。

于 2012-05-19T11:49:48.627 に答える