ホームページ  >  記事  >  Java  >  非同期タスク実行内でリクエストスコープの Bean にアクセスするにはどうすればよいですか?

非同期タスク実行内でリクエストスコープの Bean にアクセスするにはどうすればよいですか?

Mary-Kate Olsen
Mary-Kate Olsenオリジナル
2024-10-31 01:54:01795ブラウズ

How to access request-scoped beans within asynchronous task execution?

非同期タスク実行でリクエスト スコープを維持する方法

Web アプリケーションでは、Bean の使用を必要とする非同期操作を実行するのが一般的ですリクエストスコープ付き。非同期タスク実行でリクエスト スコープを有効にするには、カスタム タスク エグゼキューターを実装します。

問題:

AsyncTaskExecutor で処理を開始する非同期 Web サービスがあります。ただし、この処理内で @Scope(value = WebApplicationContext.SCOPE_REQUEST, proxyMode = ScopedProxyMode.TARGET_CLASS) アノテーションが付けられたクラスにアクセスする必要があります。ただし、SimpleAsyncTaskExecutor でリクエスト スコープがアクティブではないため、例外が発生します。

解決策:

非同期タスクの実行でリクエスト スコープを有効にするには、以下を実装します。次の手順:

  1. カスタム TaskExecutor の作成:

    <code class="java">public class ContextAwarePoolExecutor extends ThreadPoolTaskExecutor {
        @Override
        public <T> Future<T> submit(Callable<T> task) {
            return super.submit(new ContextAwareCallable(task, RequestContextHolder.currentRequestAttributes()));
        }
    }</code>
  2. コンテキスト認識の実装呼び出し可能:

    <code class="java">public class ContextAwareCallable<T> implements Callable<T> {
        private Callable<T> task;
        private RequestAttributes context;
    
        public ContextAwareCallable(Callable<T> task, RequestAttributes context) {
            this.task = task;
            this.context = context;
        }
    
        @Override
        public T call() throws Exception {
            if (context != null) {
                RequestContextHolder.setRequestAttributes(context);
            }
    
            try {
                return task.call();
            } finally {
                RequestContextHolder.resetRequestAttributes();
            }
        }
    }</code>
  3. カスタム TaskExecutor の構成:

    <code class="java">@Configuration
    public class ExecutorConfig extends AsyncConfigurerSupport {
        @Override
        @Bean
        public Executor getAsyncExecutor() {
            return new ContextAwarePoolExecutor();
        }
    }</code>

:

ContextAwarePoolExecutor は、送信されたタスクをインターセプトし、ContextAwareCallable インスタンスにラップします。これらの呼び出し可能オブジェクトは、実際のタスクを実行する前に現在のリクエスト コンテキストを設定し、その後リセットします。これにより、非同期実行中にリクエスト スコープの Bean に確実にアクセスできるようになります。

注:

  • このソリューションは、セッション スコープとリクエスト スコープの両方で機能します。
  • 実行可能な実装を作成し、execute() メソッドの呼び出し可能な実装の代わりに使用できます。

以上が非同期タスク実行内でリクエストスコープの Bean にアクセスするにはどうすればよいですか?の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

声明:
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。