mirror of
https://github.com/apache/struts.git
synced 2026-08-07 07:37:20 +00:00
WW-5512 Supports mixing required and optional parameters in any order
This commit is contained in:
@@ -231,6 +231,33 @@ class ContainerImpl implements Container {
|
||||
) throws MissingDependencyException {
|
||||
final List<ParameterInjector<?>> parameterInjectors = new ArrayList<>();
|
||||
|
||||
final Iterator<Annotation[]> annotationsIterator = Arrays.asList(annotations).iterator();
|
||||
for (Class<?> parameterType : parameterTypes) {
|
||||
Inject annotation = findInject(annotationsIterator.next());
|
||||
String name = annotation == null ? defaultName : annotation.value();
|
||||
Key<?> key = Key.newInstance(parameterType, name);
|
||||
parameterInjectors.add(createParameterInjector(key, member));
|
||||
}
|
||||
|
||||
return toArray(parameterInjectors);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets parameter injectors with nulls for optional dependencies.
|
||||
*
|
||||
* @param member to which the parameters belong
|
||||
* @param annotations on the parameters
|
||||
* @param parameterTypes parameter types
|
||||
* @return injections
|
||||
*/
|
||||
<M extends AccessibleObject & Member> ParameterInjector<?>[] getParametersInjectorsWithNulls(
|
||||
M member,
|
||||
Annotation[][] annotations,
|
||||
Class<?>[] parameterTypes,
|
||||
String defaultName
|
||||
) throws MissingDependencyException {
|
||||
final List<ParameterInjector<?>> parameterInjectors = new ArrayList<>();
|
||||
|
||||
final Iterator<Annotation[]> annotationsIterator = Arrays.asList(annotations).iterator();
|
||||
for (Class<?> parameterType : parameterTypes) {
|
||||
Inject annotation = findInject(annotationsIterator.next());
|
||||
@@ -241,6 +268,8 @@ class ContainerImpl implements Container {
|
||||
} catch (MissingDependencyException e) {
|
||||
if (annotation != null && annotation.required()) {
|
||||
throw e;
|
||||
} else {
|
||||
parameterInjectors.add(createNullParameterInjector(key, member));
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -258,6 +287,23 @@ class ContainerImpl implements Container {
|
||||
return new ParameterInjector<>(externalContext, factory);
|
||||
}
|
||||
|
||||
<T> ParameterInjector<T> createNullParameterInjector(Key<T> key, Member member) throws MissingDependencyException {
|
||||
final InternalFactory<? extends T> factory = new InternalFactory<T>() {
|
||||
@Override
|
||||
public T create(InternalContext context) {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Class<? extends T> type() {
|
||||
return key.getType();
|
||||
}
|
||||
};
|
||||
|
||||
final ExternalContext<T> externalContext = ExternalContext.newInstance(member, key, this);
|
||||
return new ParameterInjector<>(externalContext, factory);
|
||||
}
|
||||
|
||||
private ParameterInjector<?>[] toArray(List<ParameterInjector<?>> parameterInjections) {
|
||||
return parameterInjections.toArray(new ParameterInjector[0]);
|
||||
}
|
||||
@@ -367,7 +413,7 @@ class ContainerImpl implements Container {
|
||||
Inject inject, ContainerImpl container, Constructor<T> constructor) throws MissingDependencyException {
|
||||
return constructor.getParameterTypes().length == 0
|
||||
? null // default constructor.
|
||||
: container.getParametersInjectors(
|
||||
: container.getParametersInjectorsWithNulls(
|
||||
constructor,
|
||||
constructor.getParameterAnnotations(),
|
||||
constructor.getParameterTypes(),
|
||||
@@ -425,18 +471,8 @@ class ContainerImpl implements Container {
|
||||
// First time through...
|
||||
constructionContext.startConstruction();
|
||||
try {
|
||||
if (constructor.getParameterCount() == 0) {
|
||||
t = constructor.newInstance();
|
||||
} else if (constructor.getParameterCount() > 0 && parameterInjectors == null) {
|
||||
t = constructor.newInstance(new Object[constructor.getParameterCount()]);
|
||||
} else if (constructor.getParameterCount() > parameterInjectors.length) {
|
||||
final Object[] parameters = getParameters(constructor, context, parameterInjectors);
|
||||
final Object[] finalParameters = Arrays.copyOf(parameters, constructor.getParameterCount());
|
||||
t = constructor.newInstance(finalParameters);
|
||||
} else {
|
||||
final Object[] parameters = getParameters(constructor, context, parameterInjectors);
|
||||
t = constructor.newInstance(parameters);
|
||||
}
|
||||
final Object[] parameters = getParameters(constructor, context, parameterInjectors);
|
||||
t = constructor.newInstance(parameters);
|
||||
constructionContext.setProxyDelegates(t);
|
||||
} finally {
|
||||
constructionContext.finishConstruction();
|
||||
|
||||
Reference in New Issue
Block a user