2

Java サーブレットで Mongo DB を使用する際に問題に直面しています。

私のサーブレットには、データを取得および追加するためにデータベースにアクセスするための多くの方法 (~20) があります。1つの非常に簡単な例:

public static String getSomething(String s) {
  String json = "[]";
  JSONArray jsonArray = new JSONArray();
  DBCollection table;

  try {
    Mongo mongo = new Mongo("localhost", 27017);
    DB db = mongo.getDB( "myDb" );  
        BasicDBObject quoteQuery = new BasicDBObject("abc", abc);
    DBCursor cursor = table.find(quoteQuery);

    try {
      while(cursor.hasNext()) {
        jsonArray.put(cursor.next());
      }
    } finally {
      cursor.close();
    }

// ...

問題は、この Java サーブレットが Linux サーバーにデプロイされると、10 日間ほど正常に動作することです。

その後、クラッシュします。

var/log ディレクトリの mongodb.log に移動すると、次の繰り返し出力が得られます。

「開いている接続が多すぎるため、接続が拒否されました」

今どこで編集すればよいのか、これにどう対処すればよいのかわかりません。サーバーで開いている接続の制限を拡大しようとしましたが、それでも同じ結果が得られます。

助言がありますか?

4

6 に答える 6

11

API ドキュメントから: http://api.mongodb.org/java/2.11.3/

public class Mongo extends Object

内部接続プールを使用したデータベース接続。ほとんどのアプリケーションでは、JVM 全体に対して 1 つの Mongo インスタンスが必要です

于 2013-09-13T11:30:58.520 に答える
3

Mongo オブジェクトは非常に慎重に作成する必要があり、理想的にはクラスローダごとに一度に 1 つだけ作成する必要があります。Mongo オブジェクトの数を減らすには、サーブレットの init メソッドでそれを作成し、すべての呼び出しでそのインスタンスを再利用します。

EDIT:コードを見て、従来のシングルトンクラスを使用してMongoインスタンスを管理します(そして、常にMongoそのクラスのgetInstance()メソッドを使用してフェッチします)。アプリに複数のサーブレット/エントリポイントがある場合、使用init()するだけでサーブレットごとに1つのインスタンスが生成されるためです、それでも@FredCloseによって引用されたマニュアルセクションを満たしていません

于 2013-09-13T11:29:28.943 に答える
1

mongo オブジェクトは、getSomething 呼び出しごとに作成するのではなく、1 回だけ作成することができます。

public SomeClass{
static Mongo mongo = new Mongo("localhost", 27017);
static DB db = mongo.getDB( "myDb" );  

public static String getSomething(String s) {
String json = "[]";
JSONArray jsonArray = new JSONArray();
DBCollection table;
try {

BasicDBObject quoteQuery = new BasicDBObject("abc", abc);
DBCursor cursor = table.find(quoteQuery);

while(cursor.hasNext()) {
  jsonArray.put(cursor.next());

}

}

実際には、静的アクセスをまったく使用せず、中央コントローラーから DB オブジェクトを注入するのが理想的なケースです。

于 2013-09-13T11:31:42.520 に答える
1

MongoDB で接続を作成していますが、接続を閉じていません。どのデータベースでも、接続を閉じることは非常に重要です。そうしないと、最大制限に達し、プログラムを適切に実行できなくなります。次のコードが役に立ちます。

        public static String getSomething(String s) {
    String json = "[]";
    JSONArray jsonArray = new JSONArray();

    try {

        MongoClient mongoClient = new MongoClient("localhost", 27017);
        DB db = mongoClient.getDB("myDb");
        DBCollection collection = db.getCollection("NAME OF YOUR COLLECTION");
        BasicDBObject quoteQuery = new BasicDBObject("abc", "VARIABLE THAT YOU WANT TO FIND");

        DBCursor cursor = collection.find(quoteQuery);
        try {
            while (cursor.hasNext()) {
                jsonArray.put(cursor.next());
            }
        } finally {
            cursor.close();
        }
        mongoClient.close();
    } catch (Exception e) {
    }
    return jsonArray.toString();
}

このコードでは、「MongoClient」はその目的が終わった後に閉じられます。

于 2013-09-13T11:50:53.693 に答える
0

アルン・グプタ @arungupta

#JavaEE7 アプリ内での Mongo の使用方法を示す新しいサンプル: Java EE アプリケーションでの Mongo の基本的な使用方法を示す新しいサンプル

于 2013-10-01T08:28:49.077 に答える