work in progress
diff --git a/src/main/java/org/apache/sling/models/impl/ModelAdapterFactory.java b/src/main/java/org/apache/sling/models/impl/ModelAdapterFactory.java
index d06787e..18c6b3e 100644
--- a/src/main/java/org/apache/sling/models/impl/ModelAdapterFactory.java
+++ b/src/main/java/org/apache/sling/models/impl/ModelAdapterFactory.java
@@ -19,23 +19,8 @@
import java.lang.ref.PhantomReference;
import java.lang.ref.ReferenceQueue;
import java.lang.ref.SoftReference;
-import java.lang.reflect.InvocationHandler;
-import java.lang.reflect.InvocationTargetException;
-import java.lang.reflect.Method;
-import java.lang.reflect.ParameterizedType;
-import java.lang.reflect.Proxy;
-import java.lang.reflect.Type;
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.Collection;
-import java.util.Collections;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.Hashtable;
-import java.util.Iterator;
-import java.util.List;
-import java.util.Map;
-import java.util.WeakHashMap;
+import java.lang.reflect.*;
+import java.util.*;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentMap;
@@ -495,6 +480,61 @@
}
}
+ @NotNull
+ private InjectableElement getElement(InjectableElement element, Type type) {
+ return new InjectableElement() {
+ @Override
+ public AnnotatedElement getAnnotatedElement() {
+ return element.getAnnotatedElement();
+ }
+
+ @Override
+ public Type getType() {
+ return type;
+ }
+
+ @Override
+ public boolean isPrimitive() {
+ return element.isPrimitive();
+ }
+
+ @Override
+ public String getName() {
+ return element.getName();
+ }
+
+ @Override
+ public String getSource() {
+ return element.getSource();
+ }
+
+ @Override
+ public String getVia() {
+ return element.getVia();
+ }
+
+ @Override
+ public Class<? extends ViaProviderType> getViaProviderType() {
+ return element.getViaProviderType();
+ }
+
+ @Override
+ public boolean hasDefaultValue() {
+ return true;
+ }
+
+ @Override
+ public Object getDefaultValue() {
+ return Optional.empty();
+ }
+
+ @Override
+ public boolean isOptional(InjectAnnotationProcessor annotationProcessor) {
+ return true;
+ }
+ };
+ }
+
private
@Nullable
RuntimeException injectElement(final InjectableElement element, final Object adaptable,
@@ -502,6 +542,26 @@
final @NotNull Map<ValuePreparer, Object> preparedValues,
final @Nullable BundleContext modelContext) {
+ Type genericType = ((InjectableField) element).getFieldGenericType();
+
+ if (genericType instanceof ParameterizedType) {
+ ParameterizedType pType = (ParameterizedType) genericType;
+ if (pType.getRawType().equals(Optional.class)) {
+ InjectableElement el = getElement(element, pType.getActualTypeArguments()[0]);
+ return injectElementInternal(el, adaptable, registry, (element1, value)
+ -> callback.inject(element, value != Optional.empty() ? Optional.ofNullable(value) : value), preparedValues, modelContext);
+ }
+ }
+ return injectElementInternal(element, adaptable, registry, callback, preparedValues, modelContext);
+ }
+
+ private
+ @Nullable
+ RuntimeException injectElementInternal(final InjectableElement element, final Object adaptable,
+ final @NotNull DisposalCallbackRegistry registry, final InjectCallback callback,
+ final @NotNull Map<ValuePreparer, Object> preparedValues,
+ final @Nullable BundleContext modelContext) {
+
InjectAnnotationProcessor annotationProcessor = null;
String source = element.getSource();
boolean wasInjectionSuccessful = false;
diff --git a/src/main/java/org/apache/sling/models/impl/injectors/ValueMapInjector.java b/src/main/java/org/apache/sling/models/impl/injectors/ValueMapInjector.java
index 92036f7..f24b367 100644
--- a/src/main/java/org/apache/sling/models/impl/injectors/ValueMapInjector.java
+++ b/src/main/java/org/apache/sling/models/impl/injectors/ValueMapInjector.java
@@ -23,7 +23,6 @@
import java.util.Arrays;
import java.util.Collection;
import java.util.List;
-import java.util.Optional;
import org.apache.commons.lang3.ClassUtils;
import org.apache.commons.lang3.ObjectUtils;
@@ -99,11 +98,6 @@
return null;
}
Class<?> collectionType = (Class<?>) pType.getRawType();
-
- if (collectionType.equals(Optional.class)) {
- return Optional.ofNullable(map.get(name));
- }
-
if (!(collectionType.equals(Collection.class) || collectionType.equals(List.class))) {
return null;
}
diff --git a/src/test/java/org/apache/sling/models/impl/OptionalObjectsTest.java b/src/test/java/org/apache/sling/models/impl/OptionalObjectsTest.java
index 13a63b6..bd4f00d 100644
--- a/src/test/java/org/apache/sling/models/impl/OptionalObjectsTest.java
+++ b/src/test/java/org/apache/sling/models/impl/OptionalObjectsTest.java
@@ -19,7 +19,6 @@
import java.util.Arrays;
import java.util.HashMap;
import java.util.Map;
-import java.util.Optional;
import org.apache.sling.api.resource.Resource;
import org.apache.sling.api.resource.ValueMap;
@@ -29,7 +28,7 @@
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.runners.MockitoJUnitRunner;
-import static org.junit.Assert.*;
+import static org.junit.Assert.assertNotNull;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.when;
@@ -60,51 +59,21 @@
map.put("optionalChar", '1');
map.put("optionalBoolean", Boolean.valueOf("true"));
map.put("optionalList", Arrays.asList("foo", "bar", "baz"));
+ map.put("optional2List", Arrays.asList("foo1", "bar1", "baz1"));
map.put("optionalArray", new String[]{"qux", "quux"});
Resource res = mock(Resource.class);
when(res.adaptTo(ValueMap.class)).thenReturn(new ValueMapDecorator(map));
+
org.apache.sling.models.testmodels.classes.OptionalObjectsModel model = factory.getAdapter(res,
org.apache.sling.models.testmodels.classes.OptionalObjectsModel.class);
assertNotNull(model);
- assertEquals(Optional.of("foo bar baz"), model.getOptionalString());
- assertEquals(Optional.empty(), model.getOptionalNullString());
-
- assertEquals(Optional.of(1), model.getOptionalInteger());
- assertEquals(Optional.empty(), model.getOptionalNullInteger());
-
- assertEquals(Optional.of(Byte.valueOf("1")), model.getOptionalByte());
- assertEquals(Optional.empty(), model.getOptionalNullByte());
-
- assertEquals(Optional.of(Long.valueOf("1")), model.getOptionalLong());
- assertEquals(Optional.empty(), model.getOptionalNullLong());
-
- assertEquals(Optional.of(Short.valueOf("1")), model.getOptionalShort());
- assertEquals(Optional.empty(), model.getOptionalNullShort());
-
- assertEquals(Optional.of(Double.valueOf("1")), model.getOptionalDouble());
- assertEquals(Optional.empty(), model.getOptionalNullDouble());
-
- assertEquals(Optional.of(Float.valueOf("1")), model.getOptionalFloat());
- assertEquals(Optional.empty(), model.getOptionalNullFloat());
-
- assertEquals(Optional.of(1L), model.getOptionalLong());
- assertEquals(Optional.empty(), model.getOptionalNullLong());
-
- assertEquals(Optional.of('1'), model.getOptionalChar());
- assertEquals(Optional.empty(), model.getOptionalNullChar());
-
- assertEquals(Optional.of(Boolean.valueOf("true")), model.getOptionalBoolean());
- assertEquals(Optional.empty(), model.getOptionalNullBoolean());
-
+ /*
assertEquals(Optional.of(Arrays.asList("foo", "bar", "baz")), model.getOptionalList());
- assertEquals(Optional.empty(), model.getOptionalNullList());
+ assertEquals(Arrays.asList("foo", "bar", "baz"), model.getOptional2List());
+ */
- assertTrue(model.getOptionalArray().isPresent());
- assertTrue("qux".equalsIgnoreCase(model.getOptionalArray().get()[0]));
- assertTrue("quux".equalsIgnoreCase(model.getOptionalArray().get()[1]));
- assertEquals(Optional.empty(), model.getOptionalNullArray());
}
}
diff --git a/src/test/java/org/apache/sling/models/testmodels/classes/OptionalObjectsModel.java b/src/test/java/org/apache/sling/models/testmodels/classes/OptionalObjectsModel.java
index a130e3d..c360004 100644
--- a/src/test/java/org/apache/sling/models/testmodels/classes/OptionalObjectsModel.java
+++ b/src/test/java/org/apache/sling/models/testmodels/classes/OptionalObjectsModel.java
@@ -16,7 +16,7 @@
*/
package org.apache.sling.models.testmodels.classes;
-import java.util.Collection;
+import java.util.List;
import java.util.Optional;
import javax.inject.Inject;
@@ -27,156 +27,16 @@
public class OptionalObjectsModel {
@Inject
- private Optional<String> optionalString;
+ private Optional<List<String>> optionalList;
@Inject
- private Optional<String> optionalNullString;
+ private List<String> optional2List;
- @Inject
- private Optional<Byte> optionalByte;
-
- @Inject
- private Optional<Byte> optionalNullByte;
-
- @Inject
- private Optional<Short> optionalShort;
-
- @Inject
- private Optional<Short> optionalNullShort;
-
- @Inject
- private Optional<Integer> optionalInteger;
-
- @Inject
- private Optional<Integer> optionalNullInteger;
-
- @Inject
- private Optional<Long> optionalLong;
-
- @Inject
- private Optional<Long> optionalNullLong;
-
- @Inject
- private Optional<Float> optionalFloat;
-
- @Inject
- private Optional<Float> optionalNullFloat;
-
- @Inject
- private Optional<Double> optionalDouble;
-
- @Inject
- private Optional<Double> optionalNullDouble;
-
- @Inject
- private Optional<Character> optionalChar;
-
- @Inject
- private Optional<Character> optionalNullChar;
-
- @Inject
- private Optional<Boolean> optionalBoolean;
-
- @Inject
- private Optional<Boolean> optionalNullBoolean;
-
- @Inject
- private Optional<? extends Collection> optionalList;
-
- @Inject
- private Optional<? extends Collection> optionalNullList;
-
- @Inject
- private Optional<String[]> optionalArray;
-
- @Inject
- private Optional<String[]> optionalNullArray;
-
- public Optional<String> getOptionalString() {
- return optionalString;
- }
-
- public Optional<String> getOptionalNullString() {
- return optionalNullString;
- }
-
- public Optional<Byte> getOptionalByte() {
- return optionalByte;
- }
-
- public Optional<Byte> getOptionalNullByte() {
- return optionalNullByte;
- }
-
- public Optional<Short> getOptionalShort() {
- return optionalShort;
- }
-
- public Optional<Short> getOptionalNullShort() {
- return optionalNullShort;
- }
-
- public Optional<Integer> getOptionalInteger() {
- return optionalInteger;
- }
-
- public Optional<Integer> getOptionalNullInteger() {
- return optionalNullInteger;
- }
-
- public Optional<Long> getOptionalLong() {
- return optionalLong;
- }
-
- public Optional<Long> getOptionalNullLong() {
- return optionalNullLong;
- }
-
- public Optional<Float> getOptionalFloat() {
- return optionalFloat;
- }
-
- public Optional<Float> getOptionalNullFloat() {
- return optionalNullFloat;
- }
-
- public Optional<Double> getOptionalDouble() {
- return optionalDouble;
- }
-
- public Optional<Double> getOptionalNullDouble() {
- return optionalNullDouble;
- }
-
- public Optional<Character> getOptionalChar() {
- return optionalChar;
- }
-
- public Optional<Character> getOptionalNullChar() {
- return optionalNullChar;
- }
-
- public Optional<Boolean> getOptionalBoolean() {
- return optionalBoolean;
- }
-
- public Optional<Boolean> getOptionalNullBoolean() {
- return optionalNullBoolean;
- }
-
- public Optional<? extends Collection> getOptionalList() {
+ public Optional<List<String>> getOptionalList() {
return optionalList;
}
- public Optional<? extends Collection> getOptionalNullList() {
- return optionalNullList;
- }
-
- public Optional<String[]> getOptionalArray() {
- return optionalArray;
- }
-
- public Optional<String[]> getOptionalNullArray() {
- return optionalNullArray;
+ public List<String> getOptional2List() {
+ return optional2List;
}
}