2012-04-26 7 views
3

ここにJavaサーブレットを話しています...私は自分の "Per Request Context"を作成していますが、 "Per Request Context"オブジェクトをThread.currentThread()。getId()値に結びつけようとしていました。ThreadId経由でスレッドの終了を検出するにはどうすればよいですか?

このコンテキストオブジェクトをどこにでも渡すのではなく、ユーザーがPer Requestベースの関数を呼び出し、そのスレッドIDのハッシュテーブルからContextオブジェクトを自動的に取得するときに、現在のスレッドIDをチェックする予定でした。

私はこのようなコードを使用します..私は()ExitContextを呼び出さない任意の潜在的なユーザから自動的に自分のアプリケーションを保護したいと思いますしかし

public void doPost(HttpServletRequest request, HttpServletResponse response) 
throws ServletException, IOException 
{ 
    MyFramework.EnterContext(); 
    try { 
     // do stuff here that leads to other classes on the same thread 
     // Access current context via static MyFramework.getCurrentContext() 
    } 
    finally { MyFramework.ExitContext(); } 
} 

C#では、スレッドオブジェクトにイベントハンドラが1x ... (私は間違っていると思いますが)スレッドが終了したときに検出またはポーリングする方法がありますか?私は現在、threadId(long)のみを格納しています。

アイデア?

+0

あなたはここにいると思います。 1つは、スレッドでやっていることが間違っていると思います。サーブレットのコンテキスト内で作業する必要があります。 – ControlAltDel

+0

ServletContextは、システムを使用するすべてのユーザー用です。 HttpSessionは現在のユーザー用です。私が必要とするのは、 "Per Request"コンテキスト、つまり同じユーザーの複数の要求です。私はフレームワークがページ上の複数の場所で使用され、非同期のロードが可能なシチュエーションを避けようとしています。使用される情報は要求ごとになるため、同時に実行されます。 – xer21

答えて

1

不幸にも、Javaのスレッドにはこのような機能は組み込まれていません。また、スレッドIDは一度に一意であることが保証されていますが、最終的にスレッドが終了すると(ドキュメントから)再利用される可能性があります。しかし、使用しているサーブレット・フレームワークは、そのような機能(投機的なもの)を実装している可能性があります。

サーブレットフィルタを実装し、ユーザにweb.xmlに含めるように指示することをお勧めします。これにより、クライアントコードが常にスレッドコンテキストで正しくラップされることを確認できます。

+0

その追加の設定の代わりに、問題があった場合には{{}が最終的に{{}をやっていなければならないと言っています。ありがとうございました – xer21

+0

WeblogicがThreadPoolを使用してスレッドを実行しているので、スレッドが実際に死ぬことはありませんでした。 weblogic(とtomcatは明らかに)スレッドをプールに戻すとき、ThreadLocal変数を削除しません。アプリケーションを再デプロイした後でのみ、アプリケーションがクリーンアップされます。最終的には、サーブレットフィルタを作成するのが唯一の安全な方法です。 (FYI)Servlets 3.0では、web.xmlを必要とせずに自動登録することができます。 – xer21

+0

私はそれが理にかなっています!自動登録について知りませんでした、便利な音! – rodion

1

ThreadLocalあなたの使用に完全に適合しているようです。 ThreadLocalオブジェクトは、スレッドごとに変数を格納する方法を提供します。このクラスの内部的な動作は、あなたが記述していることの大部分です。スレッドローカル変数を与えるためにマップを使用しています。このような

何かがトリックを行う必要があります。

あなたの他の問題については
private static final ThreadLocal<UserContext> userContext = new ThreadLocal<UserContext>(); 

public void doPost(HttpServletRequest request, HttpServletResponse response) 
       throws ServletException, IOException { 
    MyFramework.EnterContext(); 
    try { 
     UserContext context = userContext.get(); 
     //if you used the set method in this thread earlier 
     //a thread local context would be returned using get 
    } 
    finally { MyFramework.ExitContext(); } 
} 

、あなたはオブザーバーパターンを使用し、スレッドがそのタスクを完了したときに通知することができます。

+0

私はThreadLocalを研究して戻ってきます – xer21

+0

スレッドはdoPost()なのでTomcatで作成されていますので、doPost()であり、私が言いましたようにtry-finallyを行うのはユーザーにとって意味があります...しかしあなたがここで言及したことはうまくいくと思います。しかし、1つの質問ですが、私はこのメソッドで観察する必要はないようですが、これは実際にはスレッドにアタッチされているため、スレッドがなくなると自動的にコレクションに追加する必要があります。あなたの例では、これは正しかったでしょうか?または、ある時点でuserContextをnullに設定する必要がありますか? – xer21

+0

Tomcat専用の情報が見つかりました.Trackcatが削除されていない場合、新しいバージョンのtomcat> = 6.0.24はそれを閉じるよう警告します。 > = 7.0.6は実際に自動的に修正されます。したがって、このソリューションを使用してtry-finallyを使用するように指示するとうまくいくはずです。 – xer21

関連する問題