#656847 : added stub for Hibernate XML based code generation

This commit is contained in:
Timo Westkämper 2010-10-09 09:11:25 +00:00
parent 060aef301c
commit e6ec2ded0d
5 changed files with 193 additions and 15 deletions

View File

@ -0,0 +1,27 @@
package com.mysema.query.jpa.hibernate;
import java.util.Arrays;
import java.util.List;
public final class Constants {
public static final List<String> keywords = Arrays.asList(
"ABS","ALL","AND","ANY","AS","ASC","AVG","BETWEEN",
"BIT_LENGTH[51]","BOTH","BY","CASE","CHAR_LENGTH",
"CHARACTER_LENGTH","CLASS",
"COALESCE","CONCAT","COUNT","CURRENT_DATE","CURRENT_TIME",
"CURRENT_TIMESTAMP",
"DELETE","DESC","DISTINCT","ELSE","EMPTY","END","ENTRY",
"ESCAPE","EXISTS","FALSE","FETCH",
"FROM","GROUP","HAVING","IN","INDEX","INNER","IS","JOIN",
"KEY","LEADING","LEFT","LENGTH","LIKE",
"LOCATE","LOWER","MAX","MEMBER","MIN","MOD","NEW","NOT",
"NULL","NULLIF","OBJECT","OF","OR",
"ORDER","OUTER","POSITION","SELECT","SET","SIZE","SOME",
"SQRT","SUBSTRING","SUM","THEN",
"TRAILING","TRIM","TRUE","TYPE","UNKNOWN","UPDATE","UPPER",
"VALUE","WHEN","WHERE");
private Constants(){}
}

View File

@ -12,9 +12,12 @@ import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStreamWriter;
import java.io.Writer;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.Stack;
import javax.xml.stream.XMLInputFactory;
import javax.xml.stream.XMLStreamException;
@ -26,10 +29,20 @@ import org.slf4j.LoggerFactory;
import com.mysema.codegen.CodeWriter;
import com.mysema.codegen.JavaWriter;
import com.mysema.codegen.model.SimpleType;
import com.mysema.codegen.model.ClassType;
import com.mysema.codegen.model.Type;
import com.mysema.codegen.model.TypeCategory;
import com.mysema.query.QueryException;
import com.mysema.query.codegen.EmbeddableSerializer;
import com.mysema.query.codegen.EntitySerializer;
import com.mysema.query.codegen.EntityType;
import com.mysema.query.codegen.Property;
import com.mysema.query.codegen.Serializer;
import com.mysema.query.codegen.SimpleSerializerConfig;
import com.mysema.query.codegen.SupertypeSerializer;
import com.mysema.query.codegen.TypeFactory;
import com.mysema.query.codegen.TypeMappings;
import com.sun.xml.internal.ws.util.StringUtils;
/**
* @author tiwe
@ -39,6 +52,8 @@ public class HibernateDomainExporter {
private static final Logger logger = LoggerFactory.getLogger(HibernateDomainExporter.class);
private static final List<String> propertyFields = Arrays.asList("property","many-to-one","one-to-one","component","dynamic-component","properties","any","map","set","list","bag","idbag","array","primitive-array");
private final XMLInputFactory inFactory = XMLInputFactory.newInstance();
private final String namePrefix;
@ -47,39 +62,87 @@ public class HibernateDomainExporter {
private final List<EntityType> entityTypes = new ArrayList<EntityType>();
private final List<EntityType> embeddableTypes = new ArrayList<EntityType>();
private final List<EntityType> superTypes = new ArrayList<EntityType>();
private final List<File> hibernateXml;
private final TypeMappings typeMappings = new TypeMappings();
private final Serializer embeddableSerializer = new EmbeddableSerializer(typeMappings, Constants.keywords);
private final Serializer entitySerializer = new EntitySerializer(typeMappings, Constants.keywords);
private final Serializer supertypeSerializer = new SupertypeSerializer(typeMappings, Constants.keywords);
private final TypeFactory typeFactory = new TypeFactory();
public HibernateDomainExporter(String namePrefix, File targetFolder, File... hibernateXml){
this.namePrefix = namePrefix;
this.targetFolder = targetFolder;
this.hibernateXml = Arrays.asList(hibernateXml);
}
public void execute() throws FileNotFoundException, XMLStreamException{
public void execute() throws IOException {
// collect types
try {
collectTypes();
} catch (SecurityException e) {
throw new QueryException(e);
} catch (XMLStreamException e) {
throw new QueryException(e);
} catch (ClassNotFoundException e) {
throw new QueryException(e);
} catch (NoSuchMethodException e) {
throw new QueryException(e);
}
// TODO : merge supertype fields into subtypes
// serialize them
serialize(superTypes, supertypeSerializer);
serialize(embeddableTypes, embeddableSerializer);
serialize(entityTypes, entitySerializer);
}
private void serialize(List<EntityType> types, Serializer serializer) throws IOException {
for (EntityType entityType : types){
Type type = typeMappings.getPathType(entityType, entityType, true);
String packageName = entityType.getPackageName();
String className = packageName.length() > 0 ? (packageName + "." + type.getSimpleName()) : type.getSimpleName();
write(serializer, className.replace('.', '/') + ".java", entityType);
}
}
private void collectTypes() throws IOException, XMLStreamException, ClassNotFoundException, SecurityException, NoSuchMethodException {
for (File xmlFile : hibernateXml){
InputStream in = new FileInputStream(xmlFile);
XMLStreamReader reader = inFactory.createXMLStreamReader(in);
try{
EntityType entityType = null;
Stack<EntityType> types = new Stack<EntityType>();
Class<?> cl = null;
while (true) {
int event = reader.next();
if (event == START_ELEMENT) {
String name = reader.getLocalName();
if (name.equals("class")){
String className = reader.getAttributeValue(null, "name");
String packageName = className.substring(0, className.lastIndexOf("."));
String simpleName = className.substring(packageName.length());
entityType = new EntityType(namePrefix, new SimpleType(className, packageName, simpleName));
if (name.equals("class") || name.endsWith("subclass")){
cl = Class.forName(reader.getAttributeValue(null, "name"));
Type simpleType = new ClassType(TypeCategory.ENTITY, cl);
types.push(new EntityType(namePrefix, simpleType));
}else if (name.equals("property")){
}else if (propertyFields.contains(name)){
String propertyName = reader.getAttributeValue(null, "name");
// TODO
}
Type propertyType = getType(cl, propertyName);
Property property = new Property(types.peek(), propertyName, propertyType);
types.peek().addProperty(property);
}
}else if (event == END_ELEMENT){
String name = reader.getLocalName();
if (name.equals("class")){
entityTypes.add(entityType);
if (name.equals("class") || name.endsWith("subclass")){
entityTypes.add(types.peek());
types.pop();
}
} else if (event == END_DOCUMENT) {
break;
@ -90,8 +153,21 @@ public class HibernateDomainExporter {
reader.close();
}
}
// serialize entity types
}
private Type getType(Class<?> cl, String propertyName) throws NoSuchMethodException {
try {
Field field = cl.getField(propertyName);
return typeFactory.create(field.getType(), field.getGenericType());
} catch (NoSuchFieldException e) {
try{
Method method = cl.getMethod("get"+StringUtils.capitalize(propertyName));
return typeFactory.create(method.getReturnType(), method.getGenericReturnType());
}catch(NoSuchMethodException e1){
Method method = cl.getMethod("is"+StringUtils.capitalize(propertyName));
return typeFactory.create(method.getReturnType(), method.getGenericReturnType());
}
}
}
private void write(Serializer serializer, String path, EntityType type) throws IOException {

View File

@ -0,0 +1,31 @@
package com.mysema.example;
public class Contact {
private String firstName, lastName, email;
public String getFirstName() {
return firstName;
}
public void setFirstName(String firstName) {
this.firstName = firstName;
}
public String getLastName() {
return lastName;
}
public void setLastName(String lastName) {
this.lastName = lastName;
}
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
}

View File

@ -0,0 +1,27 @@
package com.mysema.query.jpa.hibernate;
import static org.junit.Assert.*;
import java.io.File;
import java.io.IOException;
import org.apache.commons.io.FileUtils;
import org.junit.Test;
public class HibernateDomainExporterTest {
@Test
public void Execute() throws IOException {
File contact = new File("src/test/resources/contact.hbm.xml");
HibernateDomainExporter exporter = new HibernateDomainExporter("Q", new File("target/gen"), contact);
exporter.execute();
File targetFile = new File("target/gen/com/mysema/example/QContact.java");
assertTrue(targetFile.exists());
String result = FileUtils.readFileToString(targetFile, "UTF-8");
System.out.println(result);
assertTrue(result.contains("StringPath firstName"));
assertTrue(result.contains("StringPath lastName"));
}
}

View File

@ -0,0 +1,17 @@
<hibernate-mapping>
<class name="com.mysema.example.Contact" table="CONTACT">
<id name="id" type="long" column="ID" >
<generator class="assigned"/>
</id>
<property name="firstName">
<column name="FIRSTNAME" />
</property>
<property name="lastName">
<column name="LASTNAME"/>
</property>
<property name="email">
<column name="EMAIL"/>
</property>
</class>
</hibernate-mapping>