spring-projects/spring-framework · error · IllegalArgumentException

Cannot use PrototypeAspectInstanceFactory with bean named

Error message

Cannot use PrototypeAspectInstanceFactory with bean named '{name}': not a prototype

What it means

Thrown as an IllegalArgumentException from the PrototypeAspectInstanceFactory constructor when the bean named in the BeanFactory is not a prototype-scoped bean (beanFactory.isPrototype(name) returns false). This factory is designed to back perthis/pertarget aspects that must yield a fresh instance each time; using it against a singleton bean would violate those semantics, so Spring rejects the mismatch at construction.

Solutions

  1. Set the bean's scope to prototype: add @Scope("prototype") or scope="prototype" in XML.
  2. If the aspect is genuinely singleton, do not use PrototypeAspectInstanceFactory; use SingletonMetadataAwareAspectInstanceFactory instead.
  3. Verify the bean name passed to the constructor resolves to the intended prototype bean.

Example fix

// before
@Bean
@Aspect("perthis(execution(* com.example.Target.*(..)))")
public static PerTargetAspect perTargetAspect() { return new PerTargetAspect(); }
// PrototypeAspectInstanceFactory(beanFactory, "perTargetAspect") throws (singleton)

// after
@Bean
@Scope("prototype")
@Aspect("perthis(execution(* com.example.Target.*(..)))")
public static PerTargetAspect perTargetAspect() { return new PerTargetAspect(); }
Defensive patterns

Strategy: validation

Validate before calling

import org.springframework.beans.factory.BeanFactory;

public static boolean isPrototype(BeanFactory bf, String name) {
    return bf.containsBean(name) && bf.isPrototype(name);
}

// before new PrototypeAspectInstanceFactory(bf, name):
if (!isPrototype(bf, name)) {
    throw new IllegalStateException("Bean '" + name + "' must be prototype-scoped");
}

Type guard

import org.springframework.beans.factory.BeanFactory;

public static boolean canUsePrototypeAspectFactory(BeanFactory bf, String name) {
    return bf.containsBean(name) && bf.isPrototype(name);
}

Try / catch

try {
    new PrototypeAspectInstanceFactory(beanFactory, name);
} catch (IllegalArgumentException ex) {
    if (ex.getMessage().contains("not a prototype")) {
        // set the bean scope to prototype or use SingletonMetadataAwareAspectInstanceFactory
    } else throw ex;
}

Prevention

When it happens

Trigger: Constructing new PrototypeAspectInstanceFactory(beanFactory, name) where the bean 'name' is singleton-scoped; BeanFactoryAspectJAdvisorsBuilder internally creating a PrototypeAspectInstanceFactory for a perthis/pertarget aspect whose bean scope was not set to prototype (companion to error 52).

Common situations: Directly instantiating PrototypeAspectInstanceFactory in framework code with a singleton bean; a misconfigured aspect where @Scope("prototype") was omitted or overridden; XML wiring pointing the factory at a singleton bean.

Related errors


AI-assisted analysis of spring-projects/spring-framework@69bf83ad71 (2026-08-09). Data as JSON: /api/errors/2670ce9c7891b7b1. Report an issue: GitHub.

Appendix: source

Thrown at spring-aop/src/main/java/org/springframework/aop/aspectj/annotation/PrototypeAspectInstanceFactory.java:50

 * @author Juergen Hoeller
 * @since 2.0
 * @see org.springframework.beans.factory.BeanFactory
 * @see LazySingletonAspectInstanceFactoryDecorator
 */
@SuppressWarnings("serial")
public class PrototypeAspectInstanceFactory extends BeanFactoryAspectInstanceFactory implements Serializable {

	/**
	 * Create a PrototypeAspectInstanceFactory. AspectJ will be called to
	 * introspect to create AJType metadata using the type returned for the
	 * given bean name from the BeanFactory.
	 * @param beanFactory the BeanFactory to obtain instance(s) from
	 * @param name the name of the bean
	 */
	public PrototypeAspectInstanceFactory(BeanFactory beanFactory, String name) {
		super(beanFactory, name);
		if (!beanFactory.isPrototype(name)) {
			throw new IllegalArgumentException(
					"Cannot use PrototypeAspectInstanceFactory with bean named '" + name + "': not a prototype");
		}
	}

}

View on GitHub (pinned to 69bf83ad71)