Je veux utiliser le mécanisme asynchrone de spring boot, voici mon code.
@Override public Future<Result> getResult(String name);
Et j'ajoute l'annotation @Async sur la méthode d'une autre classe.
@Slf4j @Configuration @EnableAsync public class AsyncConfig implements AsyncConfigurer { private static final int MAX_POOL_SIZE = 50; private static final int CORE_POOL_SIZE = 20; @Override public Executor getAsyncExecutor() { ThreadPoolTaskExecutor taskExecutor = new ThreadPoolTaskExecutor(); taskExecutor.setBeanName("taskExecutor"); taskExecutor.setMaxPoolSize(MAX_POOL_SIZE); taskExecutor.setCorePoolSize(CORE_POOL_SIZE); taskExecutor.setThreadNamePrefix("async-task-thread-pool"); taskExecutor.setWaitForTasksToCompleteOnShutdown(true); taskExecutor.setAwaitTerminationSeconds(60 * 10); taskExecutor.setRejectedExecutionHandler( (r, executor) -> log.warn("current thread pool is full, reject to invoke.")); taskExecutor.initialize(); return taskExecutor; } @Override public AsyncUncaughtExceptionHandler getAsyncUncaughtExceptionHandler() { return (ex, method, params) -> { log.error("invoke async method occurs error. method: {}, params: {}", method.getName(), JSON.toJSONString(params), ex); throw new RuntimeException(); }; } }
3 Réponses :
Ajoutez un nom à votre annotation de bean, comme @Bean (name = "taskExecutor")
. Cela devrait rendre votre bean disponible sous le nom taskExecutor. Par défaut, il enregistre un bean avec le nom methodName . Voir ici pour référence Haricot de printemps
Alors que la spécification JavaBeans utilise get
(ou est
) préfixé au nom d'une propriété pour la méthode getter, les méthodes Spring @Bean
n'utilisez pas cette convention de «traduction». Le nom de votre bean exécuteur est littéralement getAsyncExecutor
; renommez-le en taskExecutor
.
J'ai fait qu'AsyncConfigurer implémente l'interface ApplicationContextAware. Et utilisez Object getAsyncExecutor = applicationContext.getBean ("getAsyncExecutor");
dans la méthode setApplicationContext
, mais n'obtenez aucun bean nommé d'exception getAsyncExecutor. Et quand j'ai changé pour utiliser String [] beanNamesForType = applicationContext.getBeanNamesForType (Executor.class);
mais j'ai trouvé que le beanNamesForType
est vide.
Il semble que votre Application
ne soit pas une classe de configuration.
Placez le @EnableAsync
soit sur la classe qui a le
@SpringBootApplciation
ou sur une classe annotée avec @Configuration
.
J'ai changé mon code en me référant à docs.spring.io/spring-framework/docs/5.1.4.RELEASE/javadoc-a pi /… . J'ai modifié ma question et mon code, mais ne fonctionne toujours pas.
Voulez-vous publier votre dépôt source?
Désolé, le code n'est pas autorisé à exposer.
Vous devez soit changer le nom de la méthode qui enregistre le bean comme
public Executor taskExecutor ()
depuispublic Executor getAsyncExecutor ()
soit nommer votre bean comme "taskExecutor" par exemple@Bean (name = "taskExecutor") public Executor getAsyncExecutor ()