com.abiquo.commons.plugin.internal.ContextPropertiesInvocationHandler Maven / Gradle / Ivy
/**
* The Abiquo Platform
* Cloud management application for hybrid clouds
* Copyright (C) 2008 - Abiquo Holdings S.L.
*
* This application 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 under
* version 3 of the License
*
* This software 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
* LESSER GENERAL PUBLIC LICENSE v.3 for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
* Boston, MA 02111-1307, USA.
*/
package com.abiquo.commons.plugin.internal;
import static com.google.common.collect.Sets.newHashSet;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.util.Arrays;
import java.util.Collections;
import java.util.HashSet;
import java.util.Map;
import java.util.Objects;
import java.util.Set;
import com.abiquo.commons.plugin.IConnection;
import com.abiquo.commons.plugin.WithContextProperties;
import com.abiquo.commons.plugin.annotation.ContextProperties;
import com.abiquo.commons.plugin.exception.ComputeException;
import com.google.common.collect.ImmutableMap;
import com.google.common.collect.ImmutableMap.Builder;
public class ContextPropertiesInvocationHandler implements InvocationHandler
{
private final Object target;
private final Map> PROPERTIES_BY_METHODNAME;
public ContextPropertiesInvocationHandler(final Object target)
{
this.target = Objects.requireNonNull(target);
this.PROPERTIES_BY_METHODNAME = contextPropertiesByMethodName(target);
}
@Override
public Object invoke(final Object proxy, final Method method, final Object[] args)
throws UnsupportedOperationException, ComputeException
{
return new HashSet<>(PROPERTIES_BY_METHODNAME.getOrDefault(method.getName(),
Collections.emptySet()));
}
private Map> contextPropertiesByMethodName(final Object plugin)
{
Builder> builder = ImmutableMap.> builder();
if (target != null)
{
for (Method m : plugin.getClass().getMethods())
{
if (!m.isSynthetic() && !m.isBridge())
{
ContextProperties props = m.getAnnotation(ContextProperties.class);
if (props != null)
{
// IConnection should implement WithContextProperties
if (!Arrays.stream(m.getParameterTypes()).anyMatch(
c -> WithContextProperties.class.isAssignableFrom(c)
&& IConnection.class.isAssignableFrom(c)))
{
throw new IllegalStateException("Cannot load "
+ target.getClass().getSimpleName()
+ " method "
+ m.getName()
+ " uses @ContextProperties but it doesn't receive a IConnection implementing WithContextProperties");
}
builder.put(m.getName(), newHashSet(props.value()));
}
}
}
}
return builder.build();
}
}