/**
*
*/
package org.minnal.instrument.resource.creator;
import javassist.ClassPool;
import javassist.CtClass;
import javassist.bytecode.ConstPool;
import javassist.bytecode.annotation.Annotation;
import javassist.bytecode.annotation.StringMemberValue;
import javax.ws.rs.Path;
import org.minnal.instrument.MinnalInstrumentationException;
import org.minnal.instrument.NamingStrategy;
import org.minnal.instrument.resource.metadata.ResourceMetaData;
import org.minnal.instrument.util.JavassistUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import com.wordnik.swagger.annotations.Api;
/**
* @author ganeshs
*
*/
public class ResourceClassCreator {
private ResourceMetaData resource;
private Class<?> entityClass;
private String path;
private static final Logger logger = LoggerFactory.getLogger(ResourceClassCreator.class);
private ClassPool classPool = ClassPool.getDefault();
private NamingStrategy namingStrategy;
/**
* @param resource
* @param entityClass
* @param path
*/
public ResourceClassCreator(ResourceMetaData resource, NamingStrategy namingStrategy, Class<?> entityClass, String path) {
this.resource = resource;
this.entityClass = entityClass;
this.path = path;
this.namingStrategy = namingStrategy;
}
/**
* @return the resource
*/
public ResourceMetaData getResource() {
return resource;
}
/**
* @return the entityClass
*/
public Class<?> getEntityClass() {
return entityClass;
}
/**
* @return the path
*/
public String getPath() {
return path;
}
public CtClass create() {
CtClass ctClass = null;
if (resource != null) {
logger.debug("Creating the generated class for the resource {}", resource.getResourceClass());
try {
CtClass superClass = classPool.get(resource.getResourceClass().getName());
superClass.defrost();
ctClass = classPool.makeClass(namingStrategy.getResourceWrapperClassName(resource.getResourceClass()), superClass);
} catch (Exception e) {
logger.error("Failed while creating the generated class for the resource - " + resource.getResourceClass(), e);
throw new MinnalInstrumentationException("Failed while creating the generated class", e);
}
} else {
if (entityClass == null) {
logger.error("Entity Class not defined in the resource wrapper");
throw new MinnalInstrumentationException("Entity Class not defined in the resource class");
}
logger.debug("Creating the generated class for the entity {}", entityClass);
ctClass = classPool.makeClass(namingStrategy.getResourceClassName(entityClass));
}
ConstPool constPool = ctClass.getClassFile().getConstPool();
JavassistUtils.addClassAnnotations(ctClass, getApiAnnotation(constPool), getPathAnnotation(constPool));
return ctClass;
}
/**
* Returns the path annotation
*
* @param constPool
* @return
*/
protected Annotation getPathAnnotation(ConstPool constPool) {
Annotation pathAnnotation = new Annotation(Path.class.getCanonicalName(), constPool);
pathAnnotation.addMemberValue("value", new StringMemberValue(path, constPool));
return pathAnnotation;
}
/**
* Returns the api annotation
*
* @param constPool
* @return
*/
protected Annotation getApiAnnotation(ConstPool constPool) {
Annotation apiAnnotation = new Annotation(Api.class.getCanonicalName(), constPool);
apiAnnotation.addMemberValue("value", new StringMemberValue(path, constPool));
apiAnnotation.addMemberValue("description", new StringMemberValue("Operations about " + namingStrategy.getResourceName(entityClass), constPool));
return apiAnnotation;
}
}