Many resources are needed to download a project. Please understand that we have to compensate our server costs. Thank you in advance. Project price only 1 $
You can buy this project and download/modify it how often you want.
package com.michaelhradek.aurkitu.core;
import com.michaelhradek.aurkitu.Application;
import com.michaelhradek.aurkitu.annotations.*;
import com.michaelhradek.aurkitu.annotations.types.EnumType;
import com.michaelhradek.aurkitu.annotations.types.FieldType;
import com.michaelhradek.aurkitu.core.output.EnumDeclaration;
import com.michaelhradek.aurkitu.core.output.Schema;
import com.michaelhradek.aurkitu.core.output.TypeDeclaration;
import com.michaelhradek.aurkitu.core.output.TypeDeclaration.Property;
import com.michaelhradek.aurkitu.core.output.TypeDeclaration.Property.PropertyOptionKey;
import lombok.Getter;
import org.apache.maven.artifact.DependencyResolutionRequiredException;
import org.apache.maven.plugin.MojoExecutionException;
import org.apache.maven.project.MavenProject;
import java.io.File;
import java.io.IOException;
import java.lang.annotation.Annotation;
import java.lang.reflect.Field;
import java.lang.reflect.Type;
import java.net.URL;
import java.net.URLClassLoader;
import java.util.*;
import java.util.Map.Entry;
/**
* @author m.hradek
*
*/
@Getter
public class Processor {
private List> sourceAnnotations;
private Set> targetClasses;
private ArtifactReference artifactReference;
private Set warnedTypeNames;
private Map namespaceOverrideMap;
private List specifiedDependencies;
private Schema schema;
public Processor() {
sourceAnnotations = new ArrayList>();
targetClasses = new HashSet>();
warnedTypeNames = new HashSet();
// This could be null as the value via Application could be overriden here
namespaceOverrideMap = new HashMap();
}
/**
* @param targetAnnotation Add Aurkitu annotation to process.
* @return an instance of the Processor object
*/
public Processor withSourceAnnotation(Class extends Annotation> targetAnnotation) {
sourceAnnotations.add(targetAnnotation);
return this;
}
/**
*
* @param artifactReference The ArtifactReference component
* @return an instance of the Processor object
*/
public Processor withArtifactReference(ArtifactReference artifactReference) {
this.artifactReference = artifactReference;
return this;
}
/**
* By setting this we override namespaces found while building TypeDeclaration
*
* @param namespaceOverrideMap The namespace map
* @return an instance of the Processor object
*/
public Processor withNamespaceOverrideMap(Map namespaceOverrideMap) {
if (namespaceOverrideMap == null) {
return this;
}
// Formatting the input so it is consistent
Map temp = new HashMap();
for (Entry item : namespaceOverrideMap.entrySet()) {
Application.getLogger().debug(String.format("Reviewing namespaceOverrideMap item key: %s, value %s",
item.getKey(), item.getValue()));
temp.put(item.getKey().endsWith(".") ? item.getKey() : item.getKey() + ".",
item.getValue().endsWith(".") ? item.getValue() : item.getValue() + ".");
}
this.namespaceOverrideMap = temp;
return this;
}
/**
* @param specifiedDependencies Override the default target project dependency search and only search these dependencies with this group id
* @return an instance of the Processor object
*/
public Processor withSpecifiedDependencies(List specifiedDependencies) {
if (specifiedDependencies == null) {
return this;
}
this.specifiedDependencies = specifiedDependencies;
return this;
}
/**
*
* @return a completed schema
* @throws MojoExecutionException when there is a MalformedURLException in the classpathElements
*/
public Schema buildSchema() throws MojoExecutionException {
return buildSchema(new Schema());
}
/**
* @param schema a preconfigured schema
* @return a completed schema
* @throws MojoExecutionException when there is a MalformedURLException in the classpathElements
*/
public Schema buildSchema(Schema schema) throws MojoExecutionException {
this.schema = schema;
for (Class extends Annotation> source : sourceAnnotations) {
if (artifactReference == null || artifactReference.getMavenProject() == null) {
Application.getLogger().debug("MavenProject is null; falling back to built in class scanner");
targetClasses.addAll(AnnotationParser.findAnnotatedClasses(source));
} else {
targetClasses.addAll(AnnotationParser.findAnnotatedClasses(artifactReference, source));
}
}
int rootTypeCount = 0;
for (Class> clazz : targetClasses) {
if (isEnumWorkaround(clazz)) {
schema.addEnumDeclaration(buildEnumDeclaration(clazz));
continue;
}
if (clazz instanceof Class) {
TypeDeclaration temp = buildTypeDeclaration(clazz);
if (temp.isRoot()) {
Application.getLogger().debug(" Found root: " + temp.getName());
rootTypeCount++;
if (rootTypeCount > 1) {
throw new IllegalArgumentException("Only one rootType declaration is allowed");
}
schema.setRootType(temp.getName());
}
schema.addTypeDeclaration(temp);
// Now examine inner classes
Class>[] innerClasses = clazz.getDeclaredClasses();
for (Class> inner : innerClasses) {
Application.getLogger().debug(" Processing inner class: " + inner.getSimpleName());
if (inner.isSynthetic()) {
Application.getLogger().debug(" Found synthetic...");
continue;
}
if (isEnumWorkaround(inner)) {
Application.getLogger().debug(" Found enum...");
schema.addEnumDeclaration(buildEnumDeclaration(inner));
continue;
}
Application.getLogger().debug(" Found type...");
// Inner classes cannot be root type
schema.addTypeDeclaration(buildTypeDeclaration(inner));
}
}
}
return schema;
}
/**
*
* @param enumClass Class to test if it is an Enum
* @return boolean
*/
private boolean isEnumWorkaround(Class> enumClass) {
if (enumClass.isAnonymousClass()) {
enumClass = enumClass.getSuperclass();
}
return enumClass.isEnum();
}
/**
* @param clazz Class which is being considered for an EnumDeclaration
* @return an EnumDeclaration
*/
EnumDeclaration buildEnumDeclaration(Class> clazz) {
Application.getLogger().debug("Building Enum: " + clazz.getName());
EnumDeclaration enumD = new EnumDeclaration();
enumD.setName(clazz.getSimpleName());
Annotation annotation = clazz.getAnnotation(FlatBufferEnum.class);
if (annotation instanceof FlatBufferEnum) {
FlatBufferEnum myFlatBufferEnum = (FlatBufferEnum) annotation;
Application.getLogger().debug("Enum structure: " + myFlatBufferEnum.value());
enumD.setStructure(myFlatBufferEnum.value());
Application.getLogger().debug("Enum type: " + myFlatBufferEnum.enumType());
enumD.setType(myFlatBufferEnum.enumType());
} else {
Application.getLogger().debug("Not FlatBufferEnum (likely inner class); Generic enum created");
}
annotation = clazz.getAnnotation(FlatBufferComment.class);
if (annotation != null) {
String comment = ((FlatBufferComment) annotation).comment();
if (!comment.isEmpty()) {
Application.getLogger().debug("Found a comment assign to enum: " + comment);
enumD.setComment(comment);
}
}
Field[] fields = clazz.getDeclaredFields();
// Find what field was annotated as the value we need to use for the declared type
boolean setValues = false;
Field valueField = null;
int numAnnotations = 0;
if (fields != null && fields.length > 0) {
Application.getLogger().debug("Enum with declared fields detected");
for (Field field : fields) {
Application.getLogger().debug(" Field: " + field.getName() + " type:" + field.getType().getSimpleName());
if (field.getAnnotation(FlatBufferEnumTypeField.class) != null) {
Application.getLogger().debug(" Annotated field");
// Verify the declaration on the enum matches the declaration of the field
if (enumD.getType() == null) {
throw new IllegalArgumentException(
"Missing @FlatBufferEnum(enumType = EnumType.