Add support for BeanRegistrar registration on GenericApplicationContext

Closes gh-34574
This commit is contained in:
Juergen Hoeller
2025-03-11 21:18:20 +01:00
parent beb3a91847
commit 86b21d9b5c
5 changed files with 80 additions and 7 deletions

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2002-2019 the original author or authors.
* Copyright 2002-2025 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -16,6 +16,8 @@
package org.springframework.context.annotation;
import org.springframework.beans.factory.BeanRegistrar;
/**
* Common interface for annotation config application contexts,
* defining {@link #register} and {@link #scan} methods.
@@ -26,17 +28,33 @@ package org.springframework.context.annotation;
public interface AnnotationConfigRegistry {
/**
* Register one or more component classes to be processed.
* Invoke the given registrars for registering their beans with this
* application context.
* <p>This can be used to register custom beans without inferring
* annotation-based characteristics for primary/fallback/lazy-init,
* rather specifying those programmatically if needed.
* @param registrars one or more {@link BeanRegistrar} instances
* @since 7.0
* @see #register(Class[])
*/
void register(BeanRegistrar... registrars);
/**
* Register one or more component classes to be processed, inferring
* annotation-based characteristics for primary/fallback/lazy-init
* just like for scanned component classes.
* <p>Calls to {@code register} are idempotent; adding the same
* component class more than once has no additional effect.
* @param componentClasses one or more component classes,
* for example, {@link Configuration @Configuration} classes
* @see #scan(String...)
*/
void register(Class<?>... componentClasses);
/**
* Perform a scan within the specified base packages.
* @param basePackages the packages to scan for component classes
* @see #register(Class[])
*/
void scan(String... basePackages);

View File

@@ -30,6 +30,7 @@ import org.springframework.aot.hint.support.ClassHintUtils;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.BeansException;
import org.springframework.beans.factory.BeanDefinitionStoreException;
import org.springframework.beans.factory.BeanRegistrar;
import org.springframework.beans.factory.NoSuchBeanDefinitionException;
import org.springframework.beans.factory.config.AutowireCapableBeanFactory;
import org.springframework.beans.factory.config.BeanDefinition;
@@ -38,6 +39,7 @@ import org.springframework.beans.factory.config.ConfigurableListableBeanFactory;
import org.springframework.beans.factory.config.SmartInstantiationAwareBeanPostProcessor;
import org.springframework.beans.factory.support.BeanDefinitionRegistry;
import org.springframework.beans.factory.support.BeanDefinitionRegistryPostProcessor;
import org.springframework.beans.factory.support.BeanRegistryAdapter;
import org.springframework.beans.factory.support.DefaultListableBeanFactory;
import org.springframework.beans.factory.support.MergedBeanDefinitionPostProcessor;
import org.springframework.beans.factory.support.RootBeanDefinition;
@@ -594,6 +596,21 @@ public class GenericApplicationContext extends AbstractApplicationContext implem
registerBeanDefinition(nameToUse, beanDefinition);
}
/**
* Invoke the given registrars for registering their beans with this
* application context.
* <p>This can be used to apply encapsulated pieces of programmatic
* bean registration to this application context without relying on
* individual calls to its context-level {@code registerBean} methods.
* @param registrars one or more {@link BeanRegistrar} instances
* @since 7.0
*/
public void register(BeanRegistrar... registrars) {
for (BeanRegistrar registrar : registrars) {
new BeanRegistryAdapter(this.beanFactory, getEnvironment(), registrar.getClass()).register(registrar);
}
}
/**
* {@link RootBeanDefinition} subclass for {@code #registerBean} based