net.anwiba.commons.reflection.ReflectionValueProviderBuilder Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of anwiba-commons-reflaction Show documentation
Show all versions of anwiba-commons-reflaction Show documentation
anwiba commons reflaction project
/*
* #%L
* anwiba commons core
* %%
* Copyright (C) 2007 - 2016 Andreas Bartels
* %%
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as
* published by the Free Software Foundation, either version 2.1 of the
* License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Lesser Public License for more details.
*
* You should have received a copy of the GNU General Lesser Public
* License along with this program. If not, see
* .
* #L%
*/
package net.anwiba.commons.reflection;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Optional;
import java.util.Set;
import java.util.stream.Collectors;
import net.anwiba.commons.reflection.utilities.IValueHolder;
import net.anwiba.commons.reflection.utilities.ListValueHolder;
import net.anwiba.commons.reflection.utilities.SingleValueHolder;
public class ReflectionValueProviderBuilder implements IReflectionValueProviderBuilder {
private final IReflectionValueInjectionAnalyser analyser = new ReflectionValueInjectionAnalyser();
@SuppressWarnings("rawtypes")
private final Map services = new HashMap<>();
@SuppressWarnings("rawtypes")
private final Map results = new HashMap<>();
@SuppressWarnings("rawtypes")
private final Map links = new HashMap<>();
private final IReflectionValueProvider valueProvider;
public ReflectionValueProviderBuilder() {
this(new DefaultReflectionValueProvider());
}
public ReflectionValueProviderBuilder(final IReflectionValueProvider valueProvider) {
this.valueProvider = valueProvider;
}
@SuppressWarnings({ "unchecked" })
T get(final Class clazz) {
if (this.results.containsKey(clazz)) {
throw new IllegalArgumentException();
}
if (this.links.containsKey(clazz)) {
return (T) get(this.links.get(clazz));
}
if (!this.services.containsKey(clazz)) {
return this.valueProvider.get(clazz);
}
final IValueHolder valueHolder = this.services.get(clazz);
if (!(valueHolder instanceof SingleValueHolder)) {
throw new IllegalArgumentException();
}
return (T) ((SingleValueHolder) valueHolder).getValue();
}
@SuppressWarnings({ "unchecked" })
Iterable getAll(final Class clazz) {
if (this.results.containsKey(clazz)) {
throw new IllegalArgumentException();
}
if (this.links.containsKey(clazz)) {
return getAll(this.links.get(clazz));
}
if (!this.services.containsKey(clazz)) {
return this.valueProvider.getAll(clazz);
}
final IValueHolder valueHolder = this.services.get(clazz);
if (!(valueHolder instanceof ListValueHolder)) {
throw new IllegalArgumentException();
}
final List values = ((ListValueHolder) valueHolder)
.getValue()
.stream()
.map(o -> (T) o)
.collect(Collectors.toList());
values.addAll(this.valueProvider.getAll(clazz));
return values;
}
@Override
public IReflectionValueProviderBuilder link(final Class clazz, final Class extends T> link) {
if (!this.results.containsKey(clazz) && !this.services.containsKey(clazz) && !this.valueProvider.contains(clazz)) {
throw new IllegalArgumentException();
}
if (this.links.containsKey(clazz)) {
throw new IllegalArgumentException();
}
if (this.results.containsKey(link) || this.services.containsKey(link) || this.valueProvider.contains(link)) {
throw new IllegalArgumentException();
}
if (this.links.containsKey(link)) {
throw new IllegalArgumentException();
}
this.links.put(link, clazz);
return this;
}
private void checkSingleValue(final Class clazz) {
if (this.results.containsKey(clazz) || this.services.containsKey(clazz) || this.valueProvider.contains(clazz)) {
throw new IllegalArgumentException();
}
if (this.links.containsKey(clazz)) {
throw new IllegalArgumentException();
}
}
@Override
public IReflectionValueProviderBuilder set(final Class clazz, final S service) {
checkSingleValue(clazz);
this.services.put(clazz, new SingleValueHolder(service));
return this;
}
@Override
public IReflectionValueProviderBuilder set(final Class clazz, final Class extends T> serviceClass) {
checkSingleValue(clazz);
final IInjektionAnalyserResult analyserResult = this.analyser.analyse(serviceClass);
this.results.put(clazz, new SingleValueHolder(analyserResult));
return this;
}
@Override
public IReflectionValueProviderBuilder set(final Class clazz, final IInjectingFactory objectFactory) {
checkSingleValue(clazz);
final IInjektionAnalyserResult analyserResult = this.analyser.analyse(objectFactory);
this.results.put(clazz, new SingleValueHolder(analyserResult));
return this;
}
private void checkListResult(final Class clazz) {
if (this.links.containsKey(clazz)) {
throw new IllegalArgumentException();
}
if (this.services.containsKey(clazz)) {
final IValueHolder valueHolder = this.services.get(clazz);
if (!(valueHolder instanceof ListValueHolder)) {
throw new IllegalArgumentException();
}
}
if (!this.results.containsKey(clazz)) {
this.results.put(clazz, new ListValueHolder());
}
final IValueHolder valueHolder = this.results.get(clazz);
if (!(valueHolder instanceof ListValueHolder)) {
throw new IllegalArgumentException();
}
}
@Override
public IReflectionValueProviderBuilder add(final Class clazz, final IInjectingFactory objectFactory) {
checkListResult(clazz);
final IInjektionAnalyserResult analyserResult = this.analyser.analyse(objectFactory);
((ListValueHolder) this.results.get(clazz)).add(analyserResult);
return this;
}
@Override
public IReflectionValueProviderBuilder add(final Class clazz, final Class extends T> serviceClass) {
checkListResult(clazz);
final IInjektionAnalyserResult analyserResult = this.analyser.analyse(serviceClass);
((ListValueHolder) this.results.get(clazz)).add(analyserResult);
return this;
}
@Override
public IReflectionValueProviderBuilder add(final Class clazz, final S service) {
if (this.results.containsKey(clazz)) {
final IValueHolder valueHolder = this.results.get(clazz);
if (!(valueHolder instanceof ListValueHolder)) {
throw new IllegalArgumentException();
}
}
if (!this.services.containsKey(clazz)) {
this.services.put(clazz, new ListValueHolder());
}
final IValueHolder valueHolder = this.services.get(clazz);
if (!(valueHolder instanceof ListValueHolder)) {
throw new IllegalArgumentException();
}
((ListValueHolder) this.services.get(clazz)).add(service);
return this;
}
private boolean isResolveable(final IInjektionAnalyserResult analyserResult) {
if (analyserResult.isIndependent()) {
return true;
}
for (@SuppressWarnings("rawtypes")
final Class type : analyserResult.getTypes()) {
if (!this.services.containsKey(type) && !this.valueProvider.contains(type)) {
if (this.results.containsKey(type)) {
return false;
}
if (analyserResult.isNullable(type)) {
continue;
}
throw new IllegalStateException("Missing type '" + type + "' for object '" + analyserResult.getType() + "'"); //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$
}
if (!this.results.containsKey(type)) {
continue;
}
if (analyserResult.isIterable(type)) {
return false;
}
throw new IllegalStateException("Found listvalue of type '" + type //$NON-NLS-1$
+ "' for singlevalue member of object '" + analyserResult.getType() //$NON-NLS-1$
+ "'"); //$NON-NLS-1$
}
return true;
}
@SuppressWarnings("nls")
@Override
public IReflectionValueProvider build() throws CreationException {
final InjektingObjectFactory factory = InjektingObjectFactory.create(this.valueProvider, this.services, this.links);
int numberOfResults = 0;
while (!this.results.isEmpty() && numberOfResults != this.results.size()) {
@SuppressWarnings("rawtypes")
final Set keySet = new HashSet<>(this.results.keySet());
numberOfResults = this.results.size();
for (@SuppressWarnings("rawtypes")
final Class clazz : keySet) {
final IValueHolder valueHolder = this.results.get(clazz);
if (valueHolder instanceof SingleValueHolder) {
final IInjektionAnalyserResult result = (IInjektionAnalyserResult) ((SingleValueHolder) valueHolder)
.getValue();
if (isResolveable(result)) {
final Object object = factory.create(result);
this.services.put(clazz, new SingleValueHolder(object));
this.results.remove(clazz);
}
continue;
}
if (valueHolder instanceof ListValueHolder) {
final List
© 2015 - 2025 Weber Informatics LLC | Privacy Policy