2016-10-18 11 views
0

私は他のBean(ローカルインジェクション)の非同期メソッドを使用してデータを挿入するステートレスBeanを持っています。このデータの挿入には時間がかかるため、この操作を完了するまで待つことはありません。このデータの挿入後、同じBeanの別のメソッドを呼び出しています。メソッドにデバッグポイントを置くと、サーバーはこのポイントまで約90秒間待機します。 Jbossはトランザクションが非同期メソッドで完了するのを待つかもしれません。私は何が起こっているのか分からない。 。JBOSS EAP 6が非同期メソッドの後でejbメソッドを呼び出すのがブロックされました

@Stateless 
public class SimulationNodePersistenceBean implements SimulationNodePersistenceRemote, SimulationNodePersistenceLocal { 
    @Resource 
    SessionContext context; 

    @EJB 
    private SimulationResultGraphPersitenceBean graphPersistenceBean; 

    @Asynchronous 
    @TransactionAttribute(TransactionAttributeType.REQUIRED) 
    private void addResultGraphsToDatabase(long id, Graph[] graphList) { 

    ResultGraph paramGraph; 
    ResultGraphPoint dataPoint; 
    Graph graph; 
    for (int i = 0; i < graphList.length; i++) { 
     graph = graphList[i]; 
     paramGraph = new ResultGraph(); 

     try { 
      graphPersistenceBean.persistGraph(paramGraph); 
     } catch (Exception databaseException) { 
      // TODO add error message to the contingency simulation messages 
      // list 
      logger.error("Error saving ResultGraph:" + paramGraph); 
     } 
    } 
    long duration = System.nanoTime() - startTime; 
    logger.debug("Graphs inserted to DB in (sec) :" + (duration/NANO_SECOND_CONVERSION_FACTOR)); 
} 

    // @Asynchronous 
public void persistSimulationResults(long contingencySimulationId, Graph[] graphList, 
     List<AB> reiList) { 
    if (graphList != null) { 
     addResultGraphsToDatabase(contingencySimulationId, graphList); 
    } 
    if (reiList != null) { 
    //another method 
    } 
    calculateContSimStability(contingencySimulationId); 
} 

    @Override 
public void calculateSimIndex(long id) { 

} 

これはこれは、クライアントがメインbean.Thisが非同期で動作する呼び出すです

@Stateless 
public class SimulationResultGraphPersitenceBean { 
    @PersistenceContext(unitName = "DBService") 
    private EntityManager em; 

    @TransactionAttribute(TransactionAttributeType.REQUIRES_NEW) 
    @Asynchronous 
    public void persistGraph(ResultGraph graph) throws SiGuardPersistenceException { 
     try { 
      ResultGraphService service = new ResultGraphService(em); 
      service.create(graph); 
      em.flush(); 
     } catch (Exception ex) { 
      throw new PersistenceException("Error persisting graph", ex); 
     } 
    } 

メイン豆から呼び出される他のBeanです。

このメソッドを呼び出した後、私はSimulationNodePersistenceBeanの別のメソッドを呼び出します。このメソッドは数分間待機します。

getSimulationEJB().calculateSimIndex(contSimId); 

jstackを使用してスレッドダンプを作成しました。実際に私はJboss As 6ではこの問題を抱えていません。アプリケーションをJboss EAP 6に移行しました。4.設定でいくつかの設定を変更する必要があるかもしれません。しかし、私は何をすべきか分かりません。

スレッドダンプを確認しました。 BLOCKING状態でスレッドが見つかりませんでした。他のキーワードを探すべきですか?

+0

問題を説明するためのサンプルコード(または擬似コード)を提供できれば、簡単に理解できます。 –

+0

コードを追加して編集しました – user725455

+0

addResultGraphsToDatabase()メソッドの呼び出しが表示されません。私の推測では、あなたはpersistSimulationResults()からそれを呼び出すことです。 何かをする前に、実際に非同期的に呼び出されていることを確認してください(非同期メソッドと同期メソッドが混在しているため)。非同期メソッドをsessionContextから呼び出すことを忘れないでください。私はあなたがこの一般的な間違いをしていないことを確認したいだけです。こちらをご覧ください:https://satishgopal.wordpress.com/2011/04/24/ejb-3-1-asynchronous-methods/(「同期と非同期の同期」の段落をご覧ください)。お知らせ下さい。 –

答えて

1

コメントですでに指摘したように、非同期メソッドと同期メソッドの呼び出しを混在させています。あなたの例では、persistSimulationResultsメソッド(これは同期メソッドです)からaddResultGraphsToDatabaseメソッド(これはAsynchメソッドです)を呼び出しています。非同期アノテーションをコメントアウトしているためです。したがって、現在、addResultGraphsToDatabaseメソッドは、非同期アノテーションにもかかわらず、同期メソッドのように動作しています。

私がコメントに投稿したリンクを見ても、SessionContextを使用してAsynchメソッドを呼び出す必要があるかどうかはわかりません。このような何か:

クラスレベル:

@Inject 
SessionContext ctx; 

ザ・は、persistSimulationResultsメソッド内:より詳細な例については

ctx.addResultGraphsToDatabase 

、私が投稿しているリンクをご覧くださいコメントの中で。

+0

あなたの返事をありがとう。 persistSimulationResultメソッドを非同期メソッドとして定義する必要がありますか?内部から呼び出された他のメソッドが非同期に動作してはいけないので – user725455

+0

私は\t \t \tを使ってaddResultGraphsToDatabaseメソッドを呼び出そうとしています。.getBusinessObject(SimulationNodePersistenceBean.class).addResultGraphsToDatabase(contingencySimulationId、graphList);.それは違法ステート例外をスローする – user725455

+0

私があなたを助けるためにスタックトレースの最初の数行を投稿してください。 –

関連する問題