Skip to content

Instantly share code, notes, and snippets.

@mojavelinux
Created March 13, 2010 06:32
Show Gist options
  • Save mojavelinux/331154 to your computer and use it in GitHub Desktop.
Save mojavelinux/331154 to your computer and use it in GitHub Desktop.
package org.jboss.seam.bean;
import java.lang.annotation.Annotation;
import java.lang.reflect.Type;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Map;
import java.util.Set;
import javax.enterprise.event.Observes;
import javax.enterprise.inject.spi.AnnotatedConstructor;
import javax.enterprise.inject.spi.AnnotatedField;
import javax.enterprise.inject.spi.AnnotatedMethod;
import javax.enterprise.inject.spi.AnnotatedType;
import javax.enterprise.inject.spi.Extension;
import javax.enterprise.inject.spi.ProcessAnnotatedType;
import javax.enterprise.inject.spi.ProcessBean;
/**
* Alias the JSF scope annotations to the CDI scope annotations. If a JSF scope
* annotation is detected, advise the developer to update the code to use the
* equivalent CDI scope annotation. Forbid the developer from using the
* JSF managed bean annotation.
*
* @author Dan Allen
*/
public class ManagedBeanAdapterExtension implements Extension {
private Map<Class<? extends Annotation>, Class<? extends Annotation>> scopeAliasMapping;
public ManagedBeanAdapterExtension() {
scopeAliasMapping = new HashMap<Class<? extends Annotation>, Class<? extends Annotation>>(3);
scopeAliasMapping.put(javax.faces.bean.RequestScoped.class, javax.enterprise.context.RequestScoped.class);
scopeAliasMapping.put(javax.faces.bean.SessionScoped.class, javax.enterprise.context.SessionScoped.class);
scopeAliasMapping.put(javax.faces.bean.ApplicationScoped.class, javax.enterprise.context.ApplicationScoped.class);
}
public void aliasJsfScopeIfDetected(@Observes ProcessAnnotatedType<Object> annotatedType) {
for (Class<? extends Annotation> scope : scopeAliasMapping.keySet()) {
if (annotatedType.getAnnotatedType().isAnnotationPresent(scope)) {
System.out.println("WARNING: Please annotate class " + annotatedType.getAnnotatedType().getJavaClass() +
" with @" + scopeAliasMapping.get(scope).getName() + " instead of @" + scope.getName());
annotatedType.setAnnotatedType(decorateType(annotatedType.getAnnotatedType(), scope));
break;
}
}
}
public void failIfJsfManagedBeanAnnotationPresent(@Observes ProcessBean bean) {
if (bean.getAnnotated().isAnnotationPresent(javax.faces.bean.ManagedBean.class)) {
bean.addDefinitionError(new RuntimeException("Use of @javax.faces.bean.ManagedBean is forbidden. Please use @javax.inject.Named instead."));
}
}
private Class<? extends Annotation> getCdiScopeFor(Class<? extends Annotation> jsfScope) {
return scopeAliasMapping.get(jsfScope);
}
private AnnotatedType<Object> decorateType(final AnnotatedType<Object> type, final Class<? extends Annotation> jsfScope) {
final Class<? extends Annotation> cdiScope = getCdiScopeFor(jsfScope);
final Annotation cdiScopeAnnotation = new Annotation() {
@Override
public Class<? extends Annotation> annotationType() {
return cdiScope;
}
};
final Set<Annotation> maskedAnnotations = new HashSet<Annotation>(type.getAnnotations());
maskedAnnotations.remove(type.getAnnotation(jsfScope));
maskedAnnotations.add(cdiScopeAnnotation);
return new AnnotatedType<Object>() {
@Override
public Class<Object> getJavaClass() {
return type.getJavaClass();
}
@Override
public Set<AnnotatedConstructor<Object>> getConstructors() {
return type.getConstructors();
}
@Override
public Set<AnnotatedMethod<Object>> getMethods() {
return type.getMethods();
}
@Override
public Set<AnnotatedField<Object>> getFields() {
return type.getFields();
}
@Override
public Type getBaseType() {
return type.getBaseType();
}
@Override
public Set<Type> getTypeClosure() {
return type.getTypeClosure();
}
@Override
public <T extends Annotation> T getAnnotation(Class<T> annotationType) {
if (annotationType == jsfScope) {
return null;
}
else if (annotationType == cdiScope) {
return (T) cdiScopeAnnotation;
}
return type.getAnnotation(annotationType);
}
@Override
public Set<Annotation> getAnnotations() {
return maskedAnnotations;
}
@Override
public boolean isAnnotationPresent(Class<? extends Annotation> annotationType) {
if (annotationType == jsfScope) {
return false;
}
else if (annotationType == cdiScope) {
return true;
}
return type.isAnnotationPresent(annotationType);
}
};
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment