Spring Boot DelegatingSecurityContextAsyncTaskExecutor导致潜在的内存泄漏

时间:2019-05-02 09:00:23

标签: spring-boot spring-security tomcat9

在Spring Boot应用程序(2.1.4-RELEASE)中,使用TaskExecutor的以下配置

  @Primary
  @Qualifier("threadPoolTaskExecutor")
  @Bean
  public TaskExecutor threadPoolTaskExecutor() {
    final ThreadPoolTaskExecutor executor = new ThreadPoolTaskExecutor();
    executor.setCorePoolSize(10);
    executor.setMaxPoolSize(100);
    executor.setQueueCapacity(50);
    executor.setThreadNamePrefix("Foo-");
    executor.initialize();

    return new DelegatingSecurityContextAsyncTaskExecutor(executor);
  }

关闭tomcat(9.0.19)时,出现以下警告。

02-May-2019 10:34:07.384 WARNUNG [main] org.apache.catalina.loader.WebappClassLoaderBase.clearReferencesThreads The web application [myapp#bar] appears to have started a thread named [Foo-1] but has failed to stop it. This is very likely to create a memory leak. Stack trace of thread:
 java.base@11.0.2/jdk.internal.misc.Unsafe.park(Native Method)
 java.base@11.0.2/java.util.concurrent.locks.LockSupport.park(LockSupport.java:194)
 java.base@11.0.2/java.util.concurrent.locks.AbstractQueuedSynchronizer$ConditionObject.await(AbstractQueuedSynchronizer.java:2081)
 java.base@11.0.2/java.util.concurrent.LinkedBlockingQueue.take(LinkedBlockingQueue.java:433)
 java.base@11.0.2/java.util.concurrent.ThreadPoolExecutor.getTask(ThreadPoolExecutor.java:1054)
 java.base@11.0.2/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1114)
 java.base@11.0.2/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:628)
 java.base@11.0.2/java.lang.Thread.run(Thread.java:834)

删除DelegatingSecurityContextAsyncTaskExecutor后,警告消失:

  @Primary
  @Qualifier("threadPoolTaskExecutor")
  @Bean
  public TaskExecutor threadPoolTaskExecutor() {
    final ThreadPoolTaskExecutor executor = new ThreadPoolTaskExecutor();
    executor.setCorePoolSize(10);
    executor.setMaxPoolSize(100);
    executor.setQueueCapacity(50);
    executor.setThreadNamePrefix("Foo-");
    executor.initialize();

    return executor;
  }

是什么原因?怎么解决?

更新:我请原谅(请不要打扰我),但我完全忘记了这是一个Spring Boot应用程序,正在爆炸中部署在Tomcat中。我现在也尝试了Spring 2.1.4.RELEASE使用的tomcat版本9.0.17,但存在相同的问题。单独启动spring boot时,问题不会出现。

Update2 :打开了bug

2 个答案:

答案 0 :(得分:0)

您需要为线程池执行程序命名。 您会将设置归因于Springs默认线程池执行程序,因此,即使springs on thread executor现在也是异步的。

  

@Primary
  @Qualifier(“ threadPoolTask​​Executor”)

而不是定义自己的

  @Primary
  @Qualifier("appThreadPoolTaskExecutor")

答案 1 :(得分:0)

Rob Winch here回答了。