Skip to content

Commit

Permalink
Dev UI - minor improvements
Browse files Browse the repository at this point in the history
- throw an exception instead of NOT_FOUND, resolves #14872
- sort beans and observers, application components go first
- use FQCN where possible
  • Loading branch information
mkouba committed Mar 3, 2021
1 parent 3c79a05 commit ca97d65
Show file tree
Hide file tree
Showing 19 changed files with 420 additions and 190 deletions.

This file was deleted.

Original file line number Diff line number Diff line change
@@ -1,80 +1,127 @@
package io.quarkus.arc.deployment.devconsole;

import java.util.ArrayList;
import java.util.List;
import java.util.HashSet;
import java.util.Set;

public class DevBeanInfo implements Comparable<DevBeanInfo> {

private ClassName name;
private String methodName;
private DevBeanKind kind;
private ClassName type;
private List<ClassName> qualifiers = new ArrayList<>();
private ClassName scope;
import org.jboss.jandex.AnnotationInstance;
import org.jboss.jandex.AnnotationTarget;
import org.jboss.jandex.AnnotationTarget.Kind;
import org.jboss.jandex.ClassInfo;
import org.jboss.jandex.FieldInfo;
import org.jboss.jandex.MethodInfo;
import org.jboss.jandex.Type;

public DevBeanInfo() {
}
import io.quarkus.arc.deployment.CompletedApplicationClassPredicateBuildItem;
import io.quarkus.arc.processor.BeanInfo;
import io.quarkus.arc.processor.DotNames;

public DevBeanInfo(ClassName name, String methodName, ClassName type, List<ClassName> qualifiers, ClassName scope,
DevBeanKind kind) {
this.name = name;
this.methodName = methodName;
this.type = type;
this.qualifiers = qualifiers;
this.scope = scope;
this.kind = kind;
}
public class DevBeanInfo implements Comparable<DevBeanInfo> {

public void setKind(DevBeanKind kind) {
this.kind = kind;
private final DevBeanKind kind;
private final boolean isApplicationBean;
private final Name providerType;
private final String memberName;
private final Set<Name> types;
private final Set<Name> qualifiers;
private final Name scope;
private final Name declaringClass;

public DevBeanInfo(BeanInfo bean, CompletedApplicationClassPredicateBuildItem predicate) {
qualifiers = new HashSet<>();
for (AnnotationInstance qualifier : bean.getQualifiers()) {
qualifiers.add(Name.from(qualifier));
}
scope = Name.from(bean.getScope().getDotName());
types = new HashSet<>();
for (Type beanType : bean.getTypes()) {
types.add(Name.from(beanType));
}

providerType = Name.from(bean.getProviderType());

if (bean.getTarget().isPresent()) {
AnnotationTarget target = bean.getTarget().get();
if (target.kind() == Kind.METHOD) {
MethodInfo method = target.asMethod();
memberName = method.name();
this.kind = DevBeanKind.METHOD;
this.isApplicationBean = predicate.test(bean.getDeclaringBean().getBeanClass());
this.declaringClass = Name.from(bean.getDeclaringBean().getBeanClass());
} else if (target.kind() == Kind.FIELD) {
FieldInfo field = target.asField();
this.memberName = field.name();
this.kind = DevBeanKind.FIELD;
this.isApplicationBean = predicate.test(bean.getDeclaringBean().getBeanClass());
this.declaringClass = Name.from(bean.getDeclaringBean().getBeanClass());
} else if (target.kind() == Kind.CLASS) {
ClassInfo clazz = target.asClass();
this.kind = DevBeanKind.CLASS;
this.memberName = null;
this.isApplicationBean = predicate.test(clazz.name());
this.declaringClass = null;
} else {
throw new IllegalArgumentException("Invalid annotation target: " + target);
}
} else {
// Synthetic bean
this.kind = DevBeanKind.SYNTHETIC;
this.isApplicationBean = false;
this.declaringClass = null;
this.memberName = null;
}
}

public DevBeanKind getKind() {
return kind;
}

public void setScope(ClassName scope) {
this.scope = scope;
}

public ClassName getScope() {
public Name getScope() {
return scope;
}

public List<ClassName> getQualifiers() {
public Set<Name> getQualifiers() {
return qualifiers;
}

public void setQualifiers(List<ClassName> qualifiers) {
this.qualifiers = qualifiers;
}

public void setType(ClassName type) {
this.type = type;
public Set<Name> getNonDefaultQualifiers() {
Set<Name> nonDefault = new HashSet<>();
String atDefault = DotNames.DEFAULT.toString();
String atAny = DotNames.ANY.toString();
for (Name qualifier : qualifiers) {
if (qualifier.toString().endsWith(atDefault) || qualifier.toString().endsWith(atAny)) {
continue;
}
nonDefault.add(qualifier);
}
return nonDefault;
}

public ClassName getType() {
return type;
public Set<Name> getTypes() {
return types;
}

public String getMethodName() {
return methodName;
public Name getProviderType() {
return providerType;
}

public void setMethodName(String methodName) {
this.methodName = methodName;
public String getMemberName() {
return memberName;
}

public void setName(ClassName name) {
this.name = name;
public boolean isApplicationBean() {
return isApplicationBean;
}

public ClassName getName() {
return name;
public Name getDeclaringClass() {
return declaringClass;
}

@Override
public int compareTo(DevBeanInfo o) {
return type.getLocalName().compareTo(o.type.getLocalName());
// Application beans should go first
if (isApplicationBean == o.isApplicationBean) {
return providerType.compareTo(o.providerType);
}
return isApplicationBean ? -1 : 1;
}
}
Original file line number Diff line number Diff line change
@@ -1,23 +1,17 @@
package io.quarkus.arc.deployment.devconsole;

import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Optional;
import java.util.Set;

import org.jboss.jandex.AnnotationInstance;
import org.jboss.jandex.AnnotationTarget;
import org.jboss.jandex.AnnotationTarget.Kind;
import org.jboss.jandex.ClassInfo;
import org.jboss.jandex.DotName;
import org.jboss.jandex.FieldInfo;
import org.jboss.jandex.MethodInfo;

import io.quarkus.arc.deployment.AdditionalBeanBuildItem;
import io.quarkus.arc.deployment.AnnotationsTransformerBuildItem;
import io.quarkus.arc.deployment.ArcConfig;
import io.quarkus.arc.deployment.BeanDefiningAnnotationBuildItem;
import io.quarkus.arc.deployment.CompletedApplicationClassPredicateBuildItem;
import io.quarkus.arc.deployment.CustomScopeAnnotationsBuildItem;
import io.quarkus.arc.deployment.ValidationPhaseBuildItem;
import io.quarkus.arc.processor.AnnotationsTransformer;
Expand Down Expand Up @@ -94,74 +88,23 @@ public void transform(TransformationContext transformationContext) {
}

@BuildStep(onlyIf = IsDevelopment.class)
public DevConsoleTemplateInfoBuildItem collectBeanInfo(ValidationPhaseBuildItem validationPhaseBuildItem) {
public DevConsoleTemplateInfoBuildItem collectBeanInfo(ValidationPhaseBuildItem validationPhaseBuildItem,
CompletedApplicationClassPredicateBuildItem predicate) {
BeanDeploymentValidator.ValidationContext validationContext = validationPhaseBuildItem.getContext();
DevBeanInfos beanInfos = new DevBeanInfos();
for (BeanInfo beanInfo : validationContext.beans()) {
beanInfos.addBean(createBeanInfo(beanInfo));
beanInfos.addBean(new DevBeanInfo(beanInfo, predicate));
}
for (BeanInfo beanInfo : validationContext.removedBeans()) {
beanInfos.addRemovedBean(createBeanInfo(beanInfo));
beanInfos.addRemovedBean(new DevBeanInfo(beanInfo, predicate));
}
for (ObserverInfo observerInfo : validationContext.get(BuildExtension.Key.OBSERVERS)) {
beanInfos.addObserver(createDevInfo(observerInfo));
beanInfos.addObserver(new DevObserverInfo(observerInfo, predicate));
}
beanInfos.sort();
return new DevConsoleTemplateInfoBuildItem("devBeanInfos", beanInfos);
}

private DevBeanInfo createBeanInfo(BeanInfo beanInfo) {
List<ClassName> qualifiers = new ArrayList<>();
for (AnnotationInstance qualAnnotation : beanInfo.getQualifiers()) {
qualifiers.add(new ClassName(qualAnnotation.name().toString()));
}
ClassName scope = new ClassName(beanInfo.getScope().getDotName().toString());
Optional<AnnotationTarget> target = beanInfo.getTarget();
if (target.isPresent()) {
AnnotationTarget annotated = target.get();
String methodName = null;
ClassName type = null;
ClassName providerClass = null;
DevBeanKind kind = null;
if (annotated.kind() == Kind.METHOD) {
MethodInfo method = annotated.asMethod();
methodName = method.name();
type = new ClassName(method.returnType().toString());
providerClass = new ClassName(method.declaringClass().toString());
kind = DevBeanKind.METHOD;
} else if (annotated.kind() == Kind.FIELD) {
FieldInfo field = annotated.asField();
methodName = field.name();
type = new ClassName(field.type().toString());
providerClass = new ClassName(field.declaringClass().toString());
kind = DevBeanKind.FIELD;
} else if (annotated.kind() == Kind.CLASS) {
ClassInfo klass = annotated.asClass();
type = new ClassName(klass.name().toString());
kind = DevBeanKind.CLASS;
}
return new DevBeanInfo(providerClass, methodName, type, qualifiers, scope, kind);
} else {
return new DevBeanInfo(null, null, new ClassName(beanInfo.getBeanClass().toString()),
qualifiers,
scope, DevBeanKind.SYNTHETIC);
}
}

private DevObserverInfo createDevInfo(ObserverInfo observer) {
List<ClassName> qualifiers = new ArrayList<>();
ClassName name = null;
String methodName = null;
for (AnnotationInstance qualAnnotation : observer.getQualifiers()) {
qualifiers.add(new ClassName(qualAnnotation.name().toString()));
}
if (observer.getDeclaringBean() != null) {
name = new ClassName(observer.getObserverMethod().declaringClass().name().toString());
methodName = observer.getObserverMethod().name();
}
return new DevObserverInfo(name, methodName, observer.getObservedType().toString(), qualifiers, observer.getPriority(),
observer.isAsync(), observer.getReception(), observer.getTransactionPhase());
}

private boolean isAdditionalBeanDefiningAnnotationOn(ClassInfo beanClass,
List<BeanDefiningAnnotationBuildItem> beanDefiningAnnotations) {
for (BeanDefiningAnnotationBuildItem beanDefiningAnnotation : beanDefiningAnnotations) {
Expand Down
Loading

0 comments on commit ca97d65

Please sign in to comment.