private void processImport( ConfigurationClass configClass, String[] classesToImport, boolean checkForCircularImports) throws IOException { if (checkForCircularImports && this.importStack.contains(configClass)) { this.problemReporter.error( new CircularImportProblem(configClass, this.importStack, configClass.getMetadata())); } else { this.importStack.push(configClass); AnnotationMetadata importingClassMetadata = configClass.getMetadata(); for (String candidate : classesToImport) { MetadataReader reader = this.metadataReaderFactory.getMetadataReader(candidate); if (new AssignableTypeFilter(ImportSelector.class).match(reader, metadataReaderFactory)) { // the candidate class is an ImportSelector -> delegate to it to determine imports try { ImportSelector selector = BeanUtils.instantiateClass(Class.forName(candidate), ImportSelector.class); ImportSelectorContext context = new ImportSelectorContext(importingClassMetadata, this.registry); processImport(configClass, selector.selectImports(context), false); } catch (ClassNotFoundException ex) { throw new IllegalStateException(ex); } } else { // the candidate class not an ImportSelector -> process it as a @Configuration class this.importStack.registerImport(importingClassMetadata.getClassName(), candidate); processConfigurationClass(new ConfigurationClass(reader, null)); } } this.importStack.pop(); } }
private void processImports( ConfigurationClass configClass, SourceClass currentSourceClass, Collection<SourceClass> importCandidates, boolean checkForCircularImports) throws IOException { if (importCandidates.isEmpty()) { return; } if (checkForCircularImports && this.importStack.contains(configClass)) { this.problemReporter.error(new CircularImportProblem(configClass, this.importStack)); } else { this.importStack.push(configClass); try { for (SourceClass candidate : importCandidates) { if (candidate.isAssignable(ImportSelector.class)) { // Candidate class is an ImportSelector -> delegate to it to determine imports Class<?> candidateClass = candidate.loadClass(); ImportSelector selector = BeanUtils.instantiateClass(candidateClass, ImportSelector.class); invokeAwareMethods(selector); if (this.deferredImportSelectors != null && selector instanceof DeferredImportSelector) { this.deferredImportSelectors.add( new DeferredImportSelectorHolder(configClass, (DeferredImportSelector) selector)); } else { String[] importClassNames = selector.selectImports(currentSourceClass.getMetadata()); Collection<SourceClass> importSourceClasses = asSourceClasses(importClassNames); processImports(configClass, currentSourceClass, importSourceClasses, false); } } else if (candidate.isAssignable(ImportBeanDefinitionRegistrar.class)) { // Candidate class is an ImportBeanDefinitionRegistrar -> // delegate to it to register additional bean definitions Class<?> candidateClass = candidate.loadClass(); ImportBeanDefinitionRegistrar registrar = BeanUtils.instantiateClass(candidateClass, ImportBeanDefinitionRegistrar.class); invokeAwareMethods(registrar); configClass.addImportBeanDefinitionRegistrar( registrar, currentSourceClass.getMetadata()); } else { // Candidate class not an ImportSelector or ImportBeanDefinitionRegistrar -> // process it as an @Configuration class this.importStack.registerImport( currentSourceClass.getMetadata(), candidate.getMetadata().getClassName()); processConfigurationClass(candidate.asConfigClass(configClass)); } } } catch (BeanDefinitionStoreException ex) { throw ex; } catch (Exception ex) { throw new BeanDefinitionStoreException( "Failed to process import candidates for configuration class [" + configClass.getMetadata().getClassName() + "]", ex); } finally { this.importStack.pop(); } } }