87 lines
3.5 KiB
Java
87 lines
3.5 KiB
Java
package io.anuke.annotations;
|
|
|
|
import io.anuke.annotations.Annotations.ReadClass;
|
|
import io.anuke.annotations.Annotations.WriteClass;
|
|
|
|
import javax.annotation.processing.RoundEnvironment;
|
|
import javax.lang.model.element.Element;
|
|
import javax.lang.model.type.MirroredTypeException;
|
|
import javax.tools.Diagnostic.Kind;
|
|
import java.util.HashMap;
|
|
import java.util.Set;
|
|
|
|
/**This class finds reader and writer methods annotated by the {@link io.anuke.annotations.Annotations.WriteClass}
|
|
* and {@link io.anuke.annotations.Annotations.ReadClass} annotations.*/
|
|
public class IOFinder {
|
|
|
|
/**Finds all class serializers for all types and returns them. Logs errors when necessary.
|
|
* Maps fully qualified class names to their serializers.*/
|
|
public HashMap<String, ClassSerializer> findSerializers(RoundEnvironment env){
|
|
HashMap<String, ClassSerializer> result = new HashMap<>();
|
|
|
|
//get methods with the types
|
|
Set<? extends Element> writers = env.getElementsAnnotatedWith(WriteClass.class);
|
|
Set<? extends Element> readers = env.getElementsAnnotatedWith(ReadClass.class);
|
|
|
|
//look for writers first
|
|
for(Element writer : writers){
|
|
WriteClass writean = writer.getAnnotation(WriteClass.class);
|
|
String typeName = getValue(writean);
|
|
|
|
//make sure there's only one read method
|
|
if(readers.stream().filter(elem -> getValue(elem.getAnnotation(ReadClass.class)).equals(typeName)).count() > 1){
|
|
Utils.messager.printMessage(Kind.ERROR, "Multiple writer methods for type '" + typeName + "'", writer);
|
|
}
|
|
|
|
//make sure there's only one write method
|
|
long count = readers.stream().filter(elem -> getValue(elem.getAnnotation(ReadClass.class)).equals(typeName)).count();
|
|
if(count == 0){
|
|
Utils.messager.printMessage(Kind.ERROR, "Writer method does not have an accompanying reader: ", writer);
|
|
}else if(count > 1){
|
|
Utils.messager.printMessage(Kind.ERROR, "Writer method has multiple reader for type: ", writer);
|
|
}
|
|
|
|
Element reader = readers.stream().filter(elem -> getValue(elem.getAnnotation(ReadClass.class)).equals(typeName)).findFirst().get();
|
|
|
|
//add to result list
|
|
result.put(typeName, new ClassSerializer(Utils.getMethodName(reader), Utils.getMethodName(writer), typeName));
|
|
}
|
|
|
|
return result;
|
|
}
|
|
|
|
private String getValue(WriteClass write){
|
|
try {
|
|
Class<?> type = write.value();
|
|
return type.getName();
|
|
}catch (MirroredTypeException e){
|
|
return e.getTypeMirror().toString();
|
|
}
|
|
}
|
|
|
|
private String getValue(ReadClass read){
|
|
try {
|
|
Class<?> type = read.value();
|
|
return type.getName();
|
|
}catch (MirroredTypeException e){
|
|
return e.getTypeMirror().toString();
|
|
}
|
|
}
|
|
|
|
/**Information about read/write methods for a specific class type.*/
|
|
public static class ClassSerializer{
|
|
/**Fully qualified method name of the reader.*/
|
|
public final String readMethod;
|
|
/**Fully qualified method name of the writer.*/
|
|
public final String writeMethod;
|
|
/**Fully qualified class type name.*/
|
|
public final String classType;
|
|
|
|
public ClassSerializer(String readMethod, String writeMethod, String classType) {
|
|
this.readMethod = readMethod;
|
|
this.writeMethod = writeMethod;
|
|
this.classType = classType;
|
|
}
|
|
}
|
|
}
|