You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@empire-db.apache.org by do...@apache.org on 2009/10/26 23:08:19 UTC

svn commit: r829996 - in /incubator/empire-db/trunk/empire-db-codegen: ./ src/main/java/org/apache/empire/db/codegen/ src/main/java/org/apache/empire/db/codegen/types/ src/main/java/org/apache/empire/db/codegen/util/ src/main/resources/templates/

Author: doebele
Date: Mon Oct 26 22:08:18 2009
New Revision: 829996

URL: http://svn.apache.org/viewvc?rev=829996&view=rev
Log:
EMPIREDB-52 - Initial code submitted from Thomas merged

Added:
    incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/types/   (with props)
    incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/types/Column.java   (with props)
    incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/types/Database.java   (with props)
    incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/types/Table.java   (with props)
    incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/util/   (with props)
    incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/util/FileUtils.java   (with props)
    incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/util/StringUtils.java   (with props)
    incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/   (with props)
    incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/BaseRecord.vm   (with props)
    incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/BaseTable.vm   (with props)
    incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/Database.vm   (with props)
    incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/Record.vm   (with props)
    incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/Table.vm   (with props)
Modified:
    incubator/empire-db/trunk/empire-db-codegen/config.xml
    incubator/empire-db/trunk/empire-db-codegen/pom.xml
    incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/CodeGen.java
    incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/CodeGenConfig.java

Modified: incubator/empire-db/trunk/empire-db-codegen/config.xml
URL: http://svn.apache.org/viewvc/incubator/empire-db/trunk/empire-db-codegen/config.xml?rev=829996&r1=829995&r2=829996&view=diff
==============================================================================
--- incubator/empire-db/trunk/empire-db-codegen/config.xml (original)
+++ incubator/empire-db/trunk/empire-db-codegen/config.xml Mon Oct 26 22:08:18 2009
@@ -27,13 +27,18 @@
 		<jdbcURL>jdbc:oracle:thin:@192.168.0.2:1521:ora10</jdbcURL>
 		<jdbcUser>DBSAMPLE</jdbcUser>
 		<jdbcPwd>DBSAMPLE</jdbcPwd>
+
+		<!-- Schema options -->
+		<dbSchema>DBSAMPLE</dbSchema>
+		<timestampColumn></timestampColumn>
 		
 		<!-- generation options -->
-		<packageName>org.foo.db</packageName>
-		<dbClassName>MyDB</dbClassName>
-		<tableBaseName>MyTable</tableBaseName>
-		<viewBaseName>MyView</viewBaseName>
-		<recordBaseName>MyRecord</recordBaseName>
+		<targetFolder>target/generated/dbsample</targetFolder>
+		<packageName>org.apache.empire.db.samples.dbsample</packageName>
+		<dbClassName>SampleDB</dbClassName>
+		<tableBaseName>SampleTable</tableBaseName>
+		<viewBaseName>SampleView</viewBaseName>
+		<recordBaseName>SampleRecord</recordBaseName>
 		<tableClassPrefix>T</tableClassPrefix>
 		<viewClassPrefix>V</viewClassPrefix>
 		<nestTables>True</nestTables>

Modified: incubator/empire-db/trunk/empire-db-codegen/pom.xml
URL: http://svn.apache.org/viewvc/incubator/empire-db/trunk/empire-db-codegen/pom.xml?rev=829996&r1=829995&r2=829996&view=diff
==============================================================================
--- incubator/empire-db/trunk/empire-db-codegen/pom.xml (original)
+++ incubator/empire-db/trunk/empire-db-codegen/pom.xml Mon Oct 26 22:08:18 2009
@@ -32,7 +32,8 @@
 		<dependency>
 		    <groupId>org.apache.empire-db</groupId>
 		    <artifactId>empire-db</artifactId>
-		</dependency> 
+		</dependency>
+		 
 		<dependency>
 			<groupId>org.apache.velocity</groupId>
 			<artifactId>velocity</artifactId>
@@ -45,12 +46,14 @@
 		    <artifactId>hsqldb</artifactId>
 		    <!-- <scope>runtime</scope> -->
 		</dependency>
-		<!-- other  
+
+		<!-- 
 		<dependency>
 		    <groupId>ojdbc</groupId>
 		    <artifactId>ojdbc</artifactId>
 		    <version>14</version>
 		</dependency>
 		-->
+		
 	</dependencies>
 </project>
\ No newline at end of file

Modified: incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/CodeGen.java
URL: http://svn.apache.org/viewvc/incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/CodeGen.java?rev=829996&r1=829995&r2=829996&view=diff
==============================================================================
--- incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/CodeGen.java (original)
+++ incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/CodeGen.java Mon Oct 26 22:08:18 2009
@@ -18,21 +18,76 @@
  */
 package org.apache.empire.db.codegen;
 
+import java.io.File;
+import java.io.FileWriter;
+import java.io.IOException;
+import java.io.Writer;
 import java.sql.Connection;
-import java.sql.DatabaseMetaData;
 import java.sql.DriverManager;
-import java.sql.ResultSet;
 
 import org.apache.commons.logging.Log;
 import org.apache.commons.logging.LogFactory;
 import org.apache.empire.commons.ErrorObject;
+import org.apache.empire.db.codegen.types.Database;
+import org.apache.empire.db.codegen.types.Table;
+import org.apache.empire.db.codegen.util.FileUtils;
+import org.apache.velocity.Template;
+import org.apache.velocity.VelocityContext;
+import org.apache.velocity.app.Velocity;
+import org.apache.velocity.exception.ParseErrorException;
+import org.apache.velocity.exception.ResourceNotFoundException;
+
+/**
+ * This is the entry class for generating the java persistence model based on a
+ * database schema.  It uses the Empire DB open-source framework to build a 
+ * java persistence layer for an application.  The Apache Velocity template 
+ * engine is used to create the output interfaces and classes.  
+ * 
+ * The Empire DB framework doesn't try to hide the underlying database and data 
+ * model but instead embraces its power by modeling it within java.  The result 
+ * is a persistence layer that uses a more "object-oriented, type safe" SQL to
+ * access persistent data. 
+ * 
+ * NOTE:  THIS VERSION HAS SEVERE RESTRICTIONS:
+ * 1. Only tables are currently modeled (we'll add views to a later version).
+ * 2. Table indexes are not yet modeled (exception is primary key).  Again, this
+ *      will be added to later editions.
+ * 3. It is assumed that each table has a single INTEGER auto-generated primary
+ *      key column that has the same name for all tables.
+ * 4. It is assumed that each table has a single TIMESTAMP optimistic locking
+ *      column that has the same name for all tables.
+ */
 
 public class CodeGen
 {
     private static final Log log = LogFactory.getLog(CodeGen.class);
 
-    private static CodeGenConfig config = new CodeGenConfig();
-
+    // Templates
+    public static final String TEMPLATE_PATH     =    "src/main/resources/templates/";
+    public static final String DATABASE_TEMPLATE =    "Database.vm";
+    public static final String BASE_TABLE_TEMPLATE =  "BaseTable.vm";
+    public static final String TABLE_TEMPLATE =       "Table.vm";
+    public static final String BASE_RECORD_TEMPLATE = "BaseRecord.vm";
+    public static final String RECORD_TEMPLATE =      "Record.vm";
+    
+    // Properties
+    private CodeGenConfig config;
+    private File baseDir;
+    private File tableDir;
+    private File recordDir;
+    
+    /**
+     * Constructor
+     */
+    public CodeGen() {
+        try {
+            Velocity.init();
+        } catch(Exception e) {
+            log.fatal(e);
+            throw new RuntimeException(e);
+        }
+    }
+    
     /**
      * <PRE>
      * This is the entry point of the Empire-DB Sample Application
@@ -46,16 +101,20 @@
         try
         {
             // Init Configuration
+            CodeGenConfig config = new CodeGenConfig();
             config.init((args.length > 0 ? args[0] : "config.xml" ));
 
             // Enable Exceptions
             ErrorObject.setExceptionsEnabled(true);
 
             // Get a JDBC Connection
-            conn = getJDBCConnection();
+            conn = getJDBCConnection(config);
             
             // List options
             log.info("Database connection successful. Config options are:");
+            log.info("SchemaName="+String.valueOf(config.getDbSchema()));
+            log.info("TimestampColumn="+String.valueOf(config.getTimestampColumn()));
+            log.info("TargetFolder="+config.getTargetFolder());
             log.info("PackageName="+config.getPackageName());
             log.info("DbClassName="+config.getDbClassName());
             log.info("TableBaseName="+config.getTableBaseName());
@@ -65,23 +124,16 @@
             log.info("ViewClassPrefi="+config.getViewClassPrefix());
             log.info("NestTable="+config.isNestTables());
             log.info("NestViews="+config.isNestViews());
-            log.info("CreateRecordPropertie="+config.isCreateRecordProperties());
+            log.info("CreateRecordProperties="+config.isCreateRecordProperties());
             
-            // Get Metadata
-            DatabaseMetaData dmd = conn.getMetaData();
+            CodeGen codeGen = new CodeGen();
+            codeGen.generateCode(conn, config);
             
-            // Process Metadata
-            // ....
-            ResultSet rs = dmd.getCatalogs();
-            while (rs.next()) {
-                System.out.println(rs.getString(1));
-            }
-            rs.close();
+            log.info("Code generation completed sucessfully!");
             
         } catch(Exception e) {
             // Error
-            System.out.println(e.toString());
-            e.printStackTrace();
+            log.error(e.getMessage(), e);
         } finally {
             // done
             if (conn!=null)
@@ -96,7 +148,7 @@
      * Please use the config.xml file to change connection params.
      * </PRE>
      */
-    private static Connection getJDBCConnection()
+    private static Connection getJDBCConnection(CodeGenConfig config)
     {
         // Establish a new database connection
         Connection conn = null;
@@ -133,4 +185,139 @@
         }
     }
     
+    /**
+     * Generates the source code for the persistence layer.
+     */
+    public void generateCode(Connection conn, CodeGenConfig config) {
+        
+        this.config = config;
+        String packageName = config.getPackageName();
+        String targetFolder = config.getTargetFolder();
+        String dbSchema = config.getDbSchema();
+        String dbLockingCol = config.getTimestampColumn();
+        String dbPkCol = "ID"; // must be made obsolete
+        
+        Database db = new Database(conn, dbSchema);
+        db.populateTableMetaData(dbPkCol, dbLockingCol);
+        
+        // Prepare directories for generated source files
+        this.initDirectories(targetFolder, packageName);
+        
+        // Create the DB class
+        this.createDatabaseClass(db);
+    
+        // Create base table class
+        this.createBaseTableClass(db);
+
+        // Create base record class
+        this.createBaseRecordClass(db);
+        
+        // Create table classes, record interfaces and record classes
+        for (Table table: db.getTables()) {
+            this.createTableClass(db, table);
+            this.createRecordClass(db, table);
+        }
+    }
+    
+    private void initDirectories(String srcLocation, String packageName) {
+        // Create the directory structure for the generated source code.
+        File baseDir = new File(srcLocation);
+        if (!baseDir.exists()) {
+            baseDir.mkdirs();
+        }       
+        StringBuilder sb = new StringBuilder();
+        sb.append(srcLocation).append("/");
+        sb.append(packageName.replaceAll("\\.", "/"));
+        this.baseDir = new File(sb.toString());
+        if (!this.baseDir.exists()) {
+            this.baseDir.mkdirs();
+        }
+        
+        // Clean out the directory so old code is wiped out.
+        FileUtils.cleanDirectory(this.baseDir);
+        
+        // Create the table package directory
+        this.tableDir = new File(this.baseDir, "tables");
+        this.tableDir.mkdir();
+
+        // Create the record package directory
+        this.recordDir = new File(this.baseDir, "records");
+        this.recordDir.mkdir();
+    }
+    
+    private void createDatabaseClass(Database db) {
+        File file = new File(this.baseDir, db.getClassName() + ".java");
+        String packageName = config.getPackageName();
+        VelocityContext context = new VelocityContext();
+        context.put("basePackageName", packageName);       
+        context.put("tableSubPackage", "tables");
+        context.put("database", db);
+        this.writeFile(file, DATABASE_TEMPLATE, context);
+    }
+    
+    private void createBaseTableClass(Database db) {
+        File file = new File(this.tableDir,  db.getBaseTableClassName() + ".java");
+        String packageName = config.getPackageName();
+        VelocityContext context = new VelocityContext();
+        context.put("tablePackageName", packageName + ".tables");      
+        context.put("db", db);
+        this.writeFile(file, BASE_TABLE_TEMPLATE, context);
+    }
+    
+    private void createTableClass(Database db, Table table) {
+        File file = new File(this.tableDir, table.getClassName() + ".java");
+        String packageName = config.getPackageName();
+        VelocityContext context = new VelocityContext();
+        context.put("tablePackageName", packageName + ".tables");      
+        context.put("db", db);
+        context.put("table", table);
+        this.writeFile(file, TABLE_TEMPLATE, context);
+    }
+    
+    private void createBaseRecordClass(Database db) {
+        File file = new File(this.recordDir, "BaseRecord.java");
+        String packageName = config.getPackageName();
+        VelocityContext context = new VelocityContext();
+        context.put("basePackageName", packageName);       
+        context.put("tablePackageName", packageName + ".tables");      
+        context.put("recordPackage", packageName + ".records");        
+        context.put("database", db);
+        this.writeFile(file, BASE_RECORD_TEMPLATE, context);
+    }
+    
+    private void createRecordClass(Database db, Table table) {
+        File file = new File(this.recordDir, table.getRecordClassName() + ".java");
+        String packageName = config.getPackageName();
+        VelocityContext context = new VelocityContext();
+        context.put("basePackageName", packageName);       
+        context.put("tablePackageName", packageName + ".tables");      
+        context.put("recordPackage", packageName + ".records");        
+        context.put("database", db);
+        context.put("table", table);        
+        this.writeFile(file, RECORD_TEMPLATE, context);
+    }
+
+    private void writeFile(File file, String templateName, VelocityContext context) {
+        try {
+            log.info("Writing file for template: " + templateName);
+            Template template = Velocity.getTemplate(TEMPLATE_PATH + templateName);
+            Writer writer = new FileWriter(file);
+            template.merge(context, writer);
+            writer.close();
+        } catch (IOException e) {
+            log.error(e.getClass().getName()+": "+e.getMessage());
+            throw new RuntimeException(e);
+        } catch (ResourceNotFoundException e) {
+            log.error(e.getClass().getName()+": "+e.getMessage());
+            throw new RuntimeException(e);
+        } catch (ParseErrorException e) {
+            log.error(e.getClass().getName()+": "+e.getMessage());
+            throw new RuntimeException(e);
+        } catch (Exception e) {
+            log.error(e.getClass().getName()+": "+e.getMessage());
+            throw new RuntimeException(e);
+        }
+        
+    }
+    
 }

Modified: incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/CodeGenConfig.java
URL: http://svn.apache.org/viewvc/incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/CodeGenConfig.java?rev=829996&r1=829995&r2=829996&view=diff
==============================================================================
--- incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/CodeGenConfig.java (original)
+++ incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/CodeGenConfig.java Mon Oct 26 22:08:18 2009
@@ -32,6 +32,19 @@
     
     // generation options
     /**
+     * name of the database schema (may be null)
+     */
+    private String dbSchema = null;
+    /**
+     * Name of the timestamp column used for optimistic locking (may be null)
+     */
+    private String timestampColumn = null; // e.g. "UPDATE_TIMESTAMP";
+
+    /**
+     * name of the target folder
+     */
+    private String targetFolder = "target/generated/db";
+    /**
      * name of the target package
      */
     private String packageName = "org.foo.db";
@@ -154,6 +167,36 @@
     }
     
     // ------- generation options -------
+
+    public String getDbSchema()
+    {
+        return dbSchema;
+    }
+
+    public void setDbSchema(String dbSchema)
+    {
+        this.dbSchema = dbSchema;
+    }
+
+    public String getTimestampColumn()
+    {
+        return timestampColumn;
+    }
+
+    public void setTimestampColumn(String timestampColumn)
+    {
+        this.timestampColumn = timestampColumn;
+    }
+
+    public String getTargetFolder()
+    {
+        return targetFolder;
+    }
+
+    public void setTargetFolder(String targetFolder)
+    {
+        this.targetFolder = targetFolder;
+    }
     
     public String getPackageName()
     {

Propchange: incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/types/
------------------------------------------------------------------------------
    eol-style = native

Added: incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/types/Column.java
URL: http://svn.apache.org/viewvc/incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/types/Column.java?rev=829996&view=auto
==============================================================================
--- incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/types/Column.java (added)
+++ incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/types/Column.java Mon Oct 26 22:08:18 2009
@@ -0,0 +1,308 @@
+package org.apache.empire.db.codegen.types;
+
+import java.sql.ResultSet;
+import java.sql.SQLException;
+import java.sql.Types;
+
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+import org.apache.empire.data.DataType;
+import org.apache.empire.db.codegen.util.StringUtils;
+
+public class Column {
+    private static final Log log = LogFactory.getLog(Column.class);
+
+    private String name;
+	private int sqlType;
+	private int colSize;		// max length if string, precision is numeric
+	private int decimalDigits;	// max decimal digits allowed (real numbers)
+	private boolean required;
+	private String defaultValue;	
+	private String fkTableName;	// Reference parent table if column if FK
+	private boolean pkCol;
+	private boolean lockingCol;	// 
+	
+	// Java transformation
+	private String javaName;
+	private DataType empireType;
+	private String empireTypeString;
+	private String originalJavaTypeString;
+	private String javaTypeString;
+	
+	private boolean convertToBoolean;
+	private String trueValue;
+	private String falseValue;
+
+	private boolean convertToEnum;
+	
+	public String getJavaName() {
+		return javaName;
+	}
+	public void setJavaName(String javaName) {
+		this.javaName = javaName;
+	}
+	public String getJavaTypeString() {
+		return javaTypeString;
+	}
+	public String getEmpireTypeString() {
+		return empireTypeString;
+	}
+	public DataType getEmpireType() {
+		return empireType;
+	}
+	public Column(ResultSet rs) {
+		this(rs, false, false);
+	}
+	public Column(ResultSet rs, boolean primaryKey) {
+		this(rs, primaryKey, false);
+	}
+	public Column(ResultSet rs, boolean primaryKey, boolean foreignKey) {
+		if (primaryKey && foreignKey) {
+			throw new RuntimeException("Can't have a column that is both " +
+					"a primary and a foreign key.");
+		}
+		
+		try {
+			if (!primaryKey && !foreignKey) {
+				// Simple column
+				this.name = rs.getString("COLUMN_NAME").toUpperCase();
+				this.sqlType = rs.getInt("DATA_TYPE");
+				this.empireType = this.deriveJavaInfo();
+				this.colSize = rs.getInt("COLUMN_SIZE");
+				this.decimalDigits = rs.getInt("DECIMAL_DIGITS");
+				String nullable = rs.getString("IS_NULLABLE");
+				if (nullable.equalsIgnoreCase("NO"))
+					this.required = true;
+				else
+					this.required = false;
+				this.defaultValue = rs.getString("COLUMN_DEF");
+			}
+			else if (primaryKey) {
+				// Primary key column
+				this.name = rs.getString("COLUMN_NAME").toUpperCase();
+				this.sqlType = Types.INTEGER;
+				this.empireType = DataType.AUTOINC;
+				this.required = true;
+				this.javaName = StringUtils.deriveAttributeName(this.name);
+				this.javaTypeString = "Integer";
+				this.pkCol = true;
+			}
+			else {
+				// Foreign key column
+				this.name = rs.getString("FKCOLUMN_NAME").toUpperCase();
+				this.sqlType = Types.INTEGER;
+				this.empireType = DataType.INTEGER;
+				this.fkTableName = rs.getString("PKTABLE_NAME").toUpperCase();
+				this.javaName = StringUtils.deriveAttributeName(this.name);
+				this.javaTypeString = "Integer";
+			}
+			
+			this.originalJavaTypeString = this.javaTypeString;
+		}
+		catch (SQLException e) {
+			throw new RuntimeException(e);
+		}
+	}
+	@Override
+	public boolean equals(Object obj) {
+		if (obj instanceof Column) {
+			Column that = (Column)obj;
+			if (this.name.equals(that.name)) {
+				return true;
+			}
+		}
+		return false;
+	}
+	
+	public void convertToBoolean(String trueValue, String falseValue) {
+		if (this.empireType != DataType.TEXT) {
+			throw new RuntimeException(this.name + " must be a string type " +
+					"to convert to boolean");
+		}
+		this.convertToBoolean = true;
+		this.javaTypeString = "Boolean";
+		this.trueValue = trueValue;
+		this.falseValue = falseValue;
+	}
+	
+	public boolean isForeignKey() {
+		return (this.fkTableName != null);
+	}
+	public String getFkTableName() {
+		return fkTableName;
+	}
+	public String getName() {
+		return name.toUpperCase();
+	}
+	public int getSqlType() {
+		return sqlType;
+	}
+	public int getColSize() {
+		return colSize;
+	}
+	public int getDecimalDigits() {
+		return decimalDigits;
+	}
+	public boolean isRequired() {
+		return required;
+	}
+	public String getDefaultValue() {
+		if (defaultValue == null) return "null";
+		
+		return "\"" + defaultValue + "\"";
+	}
+	public boolean isLockingCol() {
+		return lockingCol;
+	}
+	public void setLockingCol(boolean lockingCol) {
+		this.lockingCol = lockingCol;
+	}
+	public boolean isPkCol() {
+		return this.pkCol;
+	}
+	public boolean isBoolean() {
+		if (this.javaTypeString.equalsIgnoreCase("Boolean"))
+			return true;
+		return false;
+	}
+	public boolean isModifiable() {
+		return (!this.isPkCol() && !this.isLockingCol());
+	}
+	
+	private DataType deriveJavaInfo() {
+		this.javaName = StringUtils.deriveAttributeName(this.name);
+		DataType empireType = DataType.UNKNOWN;
+		switch(this.sqlType) {
+		case Types.INTEGER:
+		case Types.SMALLINT:
+		case Types.TINYINT:
+		case Types.BIGINT:
+			empireType = DataType.INTEGER;
+			empireTypeString = "DataType.INTEGER";
+			javaTypeString = "Long";
+			break;
+		case Types.VARCHAR:
+			empireType = DataType.TEXT;
+			empireTypeString = "DataType.TEXT";
+			javaTypeString = "String";
+			break;
+		case Types.DATE:
+			empireType = DataType.DATE;
+			empireTypeString = "DataType.DATE";
+			javaTypeString = "Date";
+			break;
+		case Types.TIMESTAMP:
+		case Types.TIME:
+			empireType = DataType.DATETIME;
+			empireTypeString = "DataType.DATETIME";
+			javaTypeString = "Date";
+			break;
+		case Types.CHAR:
+			empireType = DataType.CHAR;
+			empireTypeString = "DataType.CHAR";
+			javaTypeString = "String";
+			break;
+		case Types.DOUBLE:
+		case Types.FLOAT:
+		case Types.REAL:
+			empireType = DataType.DOUBLE;
+			empireTypeString = "DataType.DOUBLE";
+			javaTypeString = "Double";
+			break;
+		case Types.DECIMAL:
+		case Types.NUMERIC:
+			empireType = DataType.DECIMAL;
+			empireTypeString = "DataType.DECIMAL";
+			javaTypeString = "BigDecimal";
+			break;
+		case Types.BIT:
+		case Types.BOOLEAN:
+			empireType = DataType.BOOL;
+			empireTypeString = "DataType.BOOL";
+			javaTypeString = "Boolean";
+			break;
+		case Types.CLOB:
+		case Types.LONGVARCHAR:
+			empireType = DataType.CLOB;
+			empireTypeString = "DataType.CLOB";
+			javaTypeString = "String";
+			break;
+		case Types.BINARY:
+		case Types.VARBINARY:
+		case Types.LONGVARBINARY:
+		case Types.BLOB:
+			empireType = DataType.BLOB;
+			empireTypeString = "DataType.BLOB";
+			javaTypeString = "Byte[]";
+			break;
+		default:
+			empireType = DataType.UNKNOWN;
+			empireTypeString = "DataType.UNKNOWN";
+			javaTypeString = "Byte[]";
+			System.out.println("SQL column type " + this.sqlType + " not supported.");
+		}
+		
+		return empireType;
+	}
+	public boolean isConvertToBoolean() {
+		return convertToBoolean;
+	}
+	public String getTrueValue() {
+		return trueValue;
+	}
+	public String getFalseValue() {
+		return falseValue;
+	}
+	public String getOriginalJavaTypeString() {
+		return originalJavaTypeString;
+	}
+	public boolean isConvertToEnum() {
+		return convertToEnum;
+	}
+	public String getJavaAccessorName() {
+		return StringUtils.deriveAccessorName(javaName, 
+				this.javaTypeString.equalsIgnoreCase("boolean"));
+	}
+	public String getJavaMutatorName() {
+		return StringUtils.deriveMutatorName(javaName);
+	}
+	
+	public String getReturnExpression() {
+		if (this.convertToBoolean) {
+			StringBuilder sb = new StringBuilder(this.javaName);
+			sb.append(".equalsIgnoreCase(\"");
+			sb.append(this.trueValue).append("\")");
+			return sb.toString();
+		}
+		else if (this.convertToEnum) {
+			return this.javaTypeString + ".fromDbString(" +
+			this.javaName + ")";
+		}
+		else {
+			return this.javaName;
+		}
+	}
+	public String getSetExpression() {
+		if (this.convertToBoolean) {
+			StringBuilder sb = new StringBuilder(this.javaName);
+			sb.append(" ? \"").append(this.trueValue).append("\" ");
+			sb.append(" : \"").append(this.falseValue).append("\")");
+			return sb.toString();
+		}
+		else if (this.convertToEnum) {
+			return this.javaName + ".toDbString()";
+		}
+		else {
+			return this.javaName;
+		}
+	}
+	public String getPopulateFkRecordMethodName() {
+		StringBuilder sb = new StringBuilder(this.getName());
+		StringUtils.replaceAll(sb, "_" + Table.getPkColName(),
+				"");
+		StringBuilder methodName = new StringBuilder("populate");
+		methodName.append(StringUtils.javaClassName(sb.toString()));
+		methodName.append("Record");
+		return methodName.toString();
+	}
+}

Propchange: incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/types/Column.java
------------------------------------------------------------------------------
    eol-style = native

Propchange: incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/types/Column.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/types/Database.java
URL: http://svn.apache.org/viewvc/incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/types/Database.java?rev=829996&view=auto
==============================================================================
--- incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/types/Database.java (added)
+++ incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/types/Database.java Mon Oct 26 22:08:18 2009
@@ -0,0 +1,118 @@
+package org.apache.empire.db.codegen.types;
+
+import java.sql.Connection;
+import java.sql.DatabaseMetaData;
+import java.sql.ResultSet;
+import java.sql.SQLException;
+import java.util.Collection;
+import java.util.HashMap;
+import java.util.Map;
+
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+import org.apache.empire.db.codegen.util.StringUtils;
+
+public class Database {
+    private static final Log log = LogFactory.getLog(Database.class);
+    
+    private Connection connection;
+	private String schemaName;
+	
+	private Map<String, Table> tableMap = new HashMap<String, Table>();
+
+	public Database(Connection connection, String schemaName) {
+		// Set properties
+		this.connection = connection;
+        this.schemaName = schemaName;
+	}
+	
+	public Connection getConnection() {
+	    return connection;
+	}
+	
+	private void close(ResultSet rs) {
+	    try {
+	        rs.close();
+	    } catch(SQLException e) {
+            throw new RuntimeException(e);
+	    }
+	}
+
+	/**
+	 * Populates meta data for tables in the database.
+	 * @param pkColName Primary key column name.  Note: We assume a single
+	 * 		auto-generated PK column with the same name is used for every
+	 * 		table in the DB.
+	 * @param lockColName Lock column name used for optimistic locking.
+	 * 		Note: We assume a single timestamp column with the same name 
+	 * 		is used for every table in the DB.
+	 */
+	public void populateTableMetaData(String pkColName, String lockColName) {
+		Table.setPkColName(pkColName);
+		Table.setLockColName(lockColName);
+		DatabaseMetaData dbMeta = this.getDbMetaData();
+		ResultSet tables = null;
+		try {
+            log.info("Reading Tables for schema " + schemaName);
+			tables = dbMeta.getTables(null, this.schemaName, null, new String[] {"TABLE"});
+			while (tables.next()) {
+				String tableName = tables.getString("TABLE_NAME");
+				// rd: required for oracle
+				if (tableName.indexOf('$')>=0)
+				    continue; // ignore table names with a "$"
+				// end oracle
+				log.info("Reading Table metadata for " + tableName);
+				Table table = new Table(tableName, this.schemaName, dbMeta);
+				this.tableMap.put(tableName.toUpperCase(), table);				
+			}
+			
+			for (String tableName: this.tableMap.keySet()) {
+				Table table = this.tableMap.get(tableName);
+				for (Column fkCol: table.getFkCols()) {
+					Table parentTable = this.tableMap.get(
+							fkCol.getFkTableName());
+					parentTable.addChildTable(fkCol.getName(), table);
+				}
+			}
+		} catch (SQLException e) {
+			throw new RuntimeException(e);
+		} finally {
+		    close(tables);
+		}
+	}
+	/**
+	 * Gets the database meta data.
+	 * @return The database meta data.
+	 */
+	public DatabaseMetaData getDbMetaData() {
+		try {
+			return this.getConnection().getMetaData();
+		} catch (SQLException e) {
+			e.printStackTrace();
+			throw new RuntimeException(e);
+		}
+	}
+	
+	public String getClassName() {
+		return StringUtils.javaClassName(this.schemaName) + "Database";
+	}
+
+	public String getBaseTableClassName() {
+		return StringUtils.javaClassName(this.schemaName) + "Table";
+	}
+
+	public String getInstanceName() {
+		return StringUtils.deriveAttributeNameFromClass(this.getClassName());
+	}
+
+	public Collection<Table> getTables() {
+		return tableMap.values();
+	}
+	public Table getTable(String name) {
+		return this.tableMap.get(name.toUpperCase());
+	}
+	
+	public String getSchemaName() {
+		return schemaName;
+	}
+}

Propchange: incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/types/Database.java
------------------------------------------------------------------------------
    eol-style = native

Propchange: incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/types/Database.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/types/Table.java
URL: http://svn.apache.org/viewvc/incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/types/Table.java?rev=829996&view=auto
==============================================================================
--- incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/types/Table.java (added)
+++ incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/types/Table.java Mon Oct 26 22:08:18 2009
@@ -0,0 +1,186 @@
+package org.apache.empire.db.codegen.types;
+
+import java.sql.DatabaseMetaData;
+import java.sql.ResultSet;
+import java.sql.SQLException;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+import org.apache.empire.data.DataType;
+import org.apache.empire.db.codegen.util.StringUtils;
+
+public class Table {
+    private static final Log log = LogFactory.getLog(Table.class);
+    
+    private String tableName;
+	private Column pkCol;
+	private List<Column> fkCols;
+	private List<Column> simpleCols;
+	private Column lockingCol;
+	
+	private Map<String, Column> columnMap = new HashMap<String, Column>();
+	
+	private List<Child> childTables = new ArrayList<Child>();
+	
+	private static String pkColName;
+	private static String lockColName;
+
+	public Table(String tableName, String schema, 
+			DatabaseMetaData dbMeta) {
+		this.tableName = tableName.toUpperCase();
+		this.createColumns(dbMeta, schema);
+	}
+	
+	public static String getPkColName() {
+		return pkColName;
+	}
+	public static void setPkColName(String name) {
+		pkColName = name;
+	}
+	public static String getLockColName() {
+		return lockColName;
+	}
+	public static void setLockColName(String name) {
+		lockColName = name;
+	}
+	
+	public void addChildTable(String fkColName, Table table) {
+		this.childTables.add(new Child(fkColName, table));
+	}
+	public List<Child> getChildTables() {
+		return this.childTables;
+	}
+	public String getTableName() {
+		return tableName.toUpperCase();
+	}
+
+	public Column getPkCol() {
+		return pkCol;
+	}
+
+	public List<Column> getFkCols() {
+		return fkCols;
+	}
+
+	public List<Column> getSimpleCols() {
+		return simpleCols;
+	}
+
+	public Column getLockingCol() {
+		return this.lockingCol;
+	}
+	
+	public String getClassName() {
+		return StringUtils.javaClassName(this.tableName) + "Table";
+	}
+	public String getRecordClassName() {
+		return StringUtils.javaClassName(this.tableName) + "Record";
+	}
+	public boolean hasBigDecimalField() {
+		boolean bdField = false;
+		for (Column col: this.simpleCols) {
+			if (col.getEmpireType() == DataType.DECIMAL) {
+				bdField = true;
+				break;
+			}
+		}
+		return bdField;
+	}
+	public boolean hasChildRecords() {
+		return !this.childTables.isEmpty();
+	}
+	public Column getColumn(String name) {
+		return this.columnMap.get(name.toUpperCase());
+	}
+	public static class Child {
+		Child(String fkColName, Table childTable) {
+			this.fkColName = fkColName;
+			this.childTable = childTable;
+		}
+		private String fkColName;
+		private Table childTable;
+		public String getFkColName() {
+			return fkColName.toUpperCase();
+		}
+		public Table getChildTable() {
+			return childTable;
+		}
+		public String getChildType() {
+			return StringUtils.javaClassName(childTable.getTableName());
+		}
+		public String getFkType() {
+			StringBuilder sb = new StringBuilder(this.fkColName.toUpperCase());
+			StringUtils.replaceAll(sb, "_" + Table.getPkColName(),
+					"");
+			return StringUtils.javaClassName(sb.toString());
+		}
+		public String getFkMutatorName() {
+			Column col = childTable.getColumn(this.fkColName);
+			return col.getJavaMutatorName();
+		}
+	}
+	// ------------------------------------------------------------------------
+	// Private members
+	// ------------------------------------------------------------------------
+	private void createColumns(DatabaseMetaData dbMeta, String schema) {
+		this.pkCol = this.findPkColumn(dbMeta, schema);
+		this.columnMap.put(pkCol.getName().toUpperCase(), pkCol);
+		this.simpleCols = new ArrayList<Column>();
+		this.fkCols = this.findFkColumns(dbMeta, schema);
+		for (Column col: this.fkCols) {
+			this.columnMap.put(col.getName().toUpperCase(), col);
+		}
+		try {
+			ResultSet rs = dbMeta.getColumns(null, schema, tableName, "");			
+			while (rs.next()) {
+				Column col = new Column(rs);
+				if (!col.equals(pkCol) && !fkCols.contains(col)) {
+					if (col.getName().equalsIgnoreCase(lockColName)) {
+						this.lockingCol = col;
+						col.setLockingCol(true);
+					}
+					else {
+						this.simpleCols.add(col);
+					}
+					this.columnMap.put(col.getName().toUpperCase(), col);
+				}
+			}
+		} catch (SQLException e) {
+			throw new RuntimeException(e);
+		}		
+	}
+	
+	private Column findPkColumn(DatabaseMetaData dbMeta, String schema) {
+		try {
+			ResultSet pkRs = dbMeta.getPrimaryKeys(null, schema, tableName);
+			if(pkRs.next()) {
+				Column col = new Column(pkRs, true);
+				return col;
+			}
+			else {
+				throw new RuntimeException("Primary key not found for table " +
+						this.tableName);
+			}
+
+		} catch (SQLException e) {
+			throw new RuntimeException(e);
+		}		
+	}
+	private List<Column> findFkColumns(DatabaseMetaData dbMeta, String schema) {
+		List<Column> fkCols = new ArrayList<Column>();
+		try {
+			ResultSet fkRs = dbMeta.getImportedKeys(null, schema, tableName);
+			while(fkRs.next()) {
+				Column col = new Column(fkRs, false, true);
+				fkCols.add(col);
+			}
+		} catch (SQLException e) {
+			throw new RuntimeException(e);
+		}		
+		return fkCols;
+	}
+}

Propchange: incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/types/Table.java
------------------------------------------------------------------------------
    eol-style = native

Propchange: incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/types/Table.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Propchange: incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/util/
------------------------------------------------------------------------------
    eol-style = native

Added: incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/util/FileUtils.java
URL: http://svn.apache.org/viewvc/incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/util/FileUtils.java?rev=829996&view=auto
==============================================================================
--- incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/util/FileUtils.java (added)
+++ incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/util/FileUtils.java Mon Oct 26 22:08:18 2009
@@ -0,0 +1,143 @@
+package org.apache.empire.db.codegen.util;
+
+import java.io.BufferedReader;
+import java.io.BufferedWriter;
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileNotFoundException;
+import java.io.FileOutputStream;
+import java.io.FileReader;
+import java.io.FileWriter;
+import java.io.IOException;
+import java.io.ObjectInputStream;
+import java.io.ObjectOutputStream;
+
+public class FileUtils {
+	/**
+	 * Recursively cleans (removes) all files under the given 
+	 * directory.  Note that this removes all sub-directories
+	 * but not the parent directory.  
+	 * @param directory
+	 */
+	public static void cleanDirectory(File directory) {
+		if (directory.isDirectory()) {
+            String[] children = directory.list();
+            for (int i=0; i<children.length; i++) {
+            	File child = new File(directory, children[i]);
+            	if (child.isDirectory()) deleteDirectory(child);
+            	else child.delete();
+            }
+        }
+	}
+	
+	/**
+	 * Recursively deletes a directory and everything under it.
+	 * @param directory
+	 */
+	public static void deleteDirectory(File directory) {
+        if (directory.isDirectory()) {
+            String[] children = directory.list();
+            for (int i=0; i<children.length; i++) {
+            	deleteDirectory(new File(directory, children[i]));
+            }
+        }   
+        // The directory is now empty so delete it
+        directory.delete();
+	}
+	
+	/**
+	 * Non-recursive delete for all files in the given directory.
+	 * Files in sub-directories not deleted.
+	 * @param directory
+	 */
+	public static void deleteFiles(File directory) {
+		if (directory.isDirectory()) {
+            String[] children = directory.list();
+            for (int i=0; i<children.length; i++) {
+            	new File(directory, children[i]).delete();
+            }
+        }
+	}
+	public static Object readObject(String fileName) {
+		Object o = null;
+		try {
+			ObjectInputStream ois = new ObjectInputStream(
+				new FileInputStream(fileName));
+			o = ois.readObject();
+			ois.close();
+		} catch (FileNotFoundException e) {
+			e.printStackTrace();
+		} catch (IOException e) {
+			e.printStackTrace();
+		} catch (ClassNotFoundException e) {
+			e.printStackTrace();
+		}
+		return o;
+	}
+	
+	public static void writeObject(String fileName, Object o) {
+		try {
+			ObjectOutputStream oos = new ObjectOutputStream(
+				new FileOutputStream(fileName));
+			oos.writeObject(o);
+			oos.close();
+		} catch (FileNotFoundException e) {
+			e.printStackTrace();
+		} catch (IOException e) {
+			e.printStackTrace();
+		}
+	}
+	public static String getFileAsString(File file) {
+		StringBuilder sb = new StringBuilder();
+		try {
+			BufferedReader br = new BufferedReader(
+					new FileReader(file));
+			String line;
+			while ( (line = br.readLine()) != null) {
+				sb.append(line).append("\n");
+			}
+			br.close();
+		} catch (FileNotFoundException e) {
+			e.printStackTrace();
+		} catch (IOException e) {
+			e.printStackTrace();
+		}
+		return sb.toString();
+	}
+
+	public static void writeStringToFile(File file, String contents) {
+		try {
+			if (!file.exists()) {
+				file.createNewFile();
+			}
+			BufferedWriter bw;
+			bw = new BufferedWriter(new FileWriter(file));
+			bw.write(contents);
+			bw.close();
+		} catch (IOException e) {
+			e.printStackTrace();
+		}
+
+	}
+
+	public static void replaceAll(File file, String input, String output) {
+		String fileText = getFileAsString(file);
+		StringBuilder sb = new StringBuilder(fileText);
+		int index = -1;
+		int length = input.length();
+		while ( (index = sb.indexOf(input)) != -1 ) {
+			sb.replace(index, index + length, output);
+		}
+		BufferedWriter bw;
+		try {
+			bw = new BufferedWriter(
+					new FileWriter(file));
+			bw.write(sb.toString());
+			bw.close();
+		} catch (IOException e) {
+			e.printStackTrace();
+		}
+
+	}
+
+}

Propchange: incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/util/FileUtils.java
------------------------------------------------------------------------------
    eol-style = native

Propchange: incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/util/FileUtils.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Added: incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/util/StringUtils.java
URL: http://svn.apache.org/viewvc/incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/util/StringUtils.java?rev=829996&view=auto
==============================================================================
--- incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/util/StringUtils.java (added)
+++ incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/util/StringUtils.java Mon Oct 26 22:08:18 2009
@@ -0,0 +1,86 @@
+package org.apache.empire.db.codegen.util;
+
+public class StringUtils {
+	/**
+	 * Derives a java class name from a database table name.
+	 * @param tableName
+	 * @return
+	 */
+	public static String javaClassName(String name) {
+		StringBuilder sb = new StringBuilder();
+		sb.append(Character.toUpperCase(name.charAt(0)));
+		boolean upperCase = false;
+		for (int i=1; i<name.length(); i++) {
+			char c = name.charAt(i);
+			if (c == '_') {
+				upperCase = true;
+				continue;
+			}
+			if (upperCase) sb.append(Character.toUpperCase(c));
+			else sb.append(Character.toLowerCase(c));
+			upperCase = false;
+		}
+		return sb.toString();
+	}
+	/**
+	 * Derives a java attribute name from a database column name.
+	 * @param colName
+	 * @return
+	 */
+	public static String deriveAttributeName(String colName) {
+		String name = javaClassName(colName);
+		StringBuilder sb = new StringBuilder();
+		sb.append(Character.toLowerCase(name.charAt(0)));
+		sb.append(name.substring(1));
+		return sb.toString();
+	}
+	/**
+	 * Derives an attribute name from the given class name.
+	 * @param className
+	 * @return
+	 */
+	public static String deriveAttributeNameFromClass(String className) {
+		StringBuilder sb = new StringBuilder();
+		sb.append(Character.toLowerCase(className.charAt(0)));
+		sb.append(className.substring(1));
+		return sb.toString();
+	}
+	/**
+	 * Derives the accessor method name based on the attribute name.
+	 * @param attribute
+	 * @param isBoolean
+	 * @return
+	 */
+	public static String deriveAccessorName(String attribute, boolean isBoolean) {
+		StringBuilder sb = new StringBuilder();
+		if (isBoolean) sb.append("is");
+		else sb.append("get");
+		sb.append(Character.toUpperCase(attribute.charAt(0)));
+		sb.append(attribute.substring(1));
+		return sb.toString();
+	}
+	/**
+	 * Derives the mutator method name based on the attribute name.
+	 * @param attribute
+	 * @return
+	 */
+	public static String deriveMutatorName(String attribute) {
+		StringBuilder sb = new StringBuilder();
+		sb.append("set");
+		sb.append(Character.toUpperCase(attribute.charAt(0)));
+		sb.append(attribute.substring(1));
+		return sb.toString();
+	}
+
+	public static StringBuilder replaceAll(StringBuilder sb, 
+			String oldValue, String newValue) {
+		int strIndex = sb.indexOf(oldValue);
+		int endIndex;
+		while (strIndex > -1) {
+			endIndex = strIndex + oldValue.length();
+			sb.replace(strIndex, endIndex, newValue);
+			strIndex = sb.indexOf(oldValue, strIndex);
+		}
+		return sb;
+	}
+}

Propchange: incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/util/StringUtils.java
------------------------------------------------------------------------------
    eol-style = native

Propchange: incubator/empire-db/trunk/empire-db-codegen/src/main/java/org/apache/empire/db/codegen/util/StringUtils.java
------------------------------------------------------------------------------
    svn:mime-type = text/plain

Propchange: incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/
------------------------------------------------------------------------------
    eol-style = native

Added: incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/BaseRecord.vm
URL: http://svn.apache.org/viewvc/incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/BaseRecord.vm?rev=829996&view=auto
==============================================================================
--- incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/BaseRecord.vm (added)
+++ incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/BaseRecord.vm Mon Oct 26 22:08:18 2009
@@ -0,0 +1,21 @@
+package ${recordPackage};
+
+import org.apache.empire.db.DBRecord;
+import ${tablePackageName}.${database.baseTableClassName};
+
+//import ${basePackageName}.${database.className};
+
+public abstract class BaseRecord<T extends ${database.baseTableClassName}> extends DBRecord {
+	public BaseRecord(T table) {
+		super.init(table, DBRecord.REC_EMTPY, null);
+	}
+
+	/**
+	 * Returns the table this record is based upon.
+	 * @return The table this record is based upon.
+	 */
+	@SuppressWarnings("unchecked")
+	public T getDbTable() {
+		return (T)super.getRowSet();
+	}
+}
\ No newline at end of file

Propchange: incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/BaseRecord.vm
------------------------------------------------------------------------------
    eol-style = native

Added: incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/BaseTable.vm
URL: http://svn.apache.org/viewvc/incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/BaseTable.vm?rev=829996&view=auto
==============================================================================
--- incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/BaseTable.vm (added)
+++ incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/BaseTable.vm Mon Oct 26 22:08:18 2009
@@ -0,0 +1,10 @@
+package $tablePackageName;
+
+import org.apache.empire.db.DBDatabase;
+import org.apache.empire.db.DBTable;
+
+public class ${db.baseTableClassName} extends DBTable {
+	public ${db.baseTableClassName}(String name, DBDatabase db) {
+		super(name, db);
+	}
+}

Propchange: incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/BaseTable.vm
------------------------------------------------------------------------------
    eol-style = native

Added: incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/Database.vm
URL: http://svn.apache.org/viewvc/incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/Database.vm?rev=829996&view=auto
==============================================================================
--- incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/Database.vm (added)
+++ incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/Database.vm Mon Oct 26 22:08:18 2009
@@ -0,0 +1,105 @@
+package $basePackageName;
+
+import java.sql.Connection;
+
+import java.util.List;
+import java.util.ArrayList;
+
+import org.apache.empire.db.DBCommand;
+import org.apache.empire.db.DBDatabase;
+import org.apache.empire.db.DBReader;
+import org.apache.empire.db.DBRecord;
+
+import $basePackageName.$tableSubPackage.*;
+
+public class $database.className extends DBDatabase {
+#foreach($table in $database.tables)
+	public final $table.className T_$table.tableName = new ${table.className}(this);
+#end
+	
+	/**
+	 * Returns the instance of the database.
+	 * @return
+	 */
+	public static $database.className get() {
+		if (instance == null) {
+			instance = new GamesDatabase();
+		}
+		return instance;
+	}
+	
+	/**
+	 * Default constructor for the $database.className.  Relationship between the
+	 * tables that make up the database are specified here. 
+	 */
+	private ${database.className}() {
+		// FK relationships
+#foreach($table in $database.tables)
+#foreach($fkCol in $table.fkCols)
+		super.addRelation(T_${table.tableName}.${fkCol.name}.referenceOn(T_${fkCol.fkTableName}.${table.pkColName}));
+#end
+#end
+	}
+	
+	/**
+	 * Convenience method that returns a single DB record based on a given 
+	 * command (i.e. query).  Only use this method for queries that should only
+	 * return a single value. 
+	 * @param <T> The DB record type.
+	 * @param recordType The DB record class.
+	 * @param command The command (or query) to execute.
+	 * @return 
+	 */
+	public <T extends DBRecord> T findRecord(Class<T> recordType, 
+			DBCommand command, Connection conn) {
+		DBReader reader = new DBReader();
+		T record = null;
+		try {
+			if (reader.getRecordData(command, conn)) {
+				record = recordType.newInstance();
+				reader.initRecord(record.getRowSet(), record);
+			}
+		} catch (InstantiationException e) {
+			throw new RuntimeException(e);
+		} catch (IllegalAccessException e) {
+			throw new RuntimeException(e);
+		}
+		finally {
+			reader.close();
+		}	
+		return record;
+	}
+	
+	/**
+	 * Convenience method that returns a list of DB records based on a given 
+	 * command (i.e. query).
+	 * @param <T> The DB record type.
+	 * @param recordType The DB record class.
+	 * @param command The command (or query) to execute.
+	 * @return 
+	 */
+	public <T extends DBRecord> List<T> findRecords(Class<T> recordType, 
+			DBCommand command, Connection conn) {
+		List<T> records = new ArrayList<T>();
+		DBReader reader = new DBReader();
+		try {
+			reader.open(command, conn);
+			while (reader.moveNext()) {
+				T record = recordType.newInstance();
+				reader.initRecord(record.getRowSet(), record);
+				records.add(record);
+			}
+		} catch (InstantiationException e) {
+			throw new RuntimeException(e);
+		} catch (IllegalAccessException e) {
+			throw new RuntimeException(e);
+		}
+		finally {
+			reader.close();
+		}
+		return records;
+	}
+		
+	private static $database.className instance;
+	private static final long serialVersionUID = 1L;
+}

Propchange: incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/Database.vm
------------------------------------------------------------------------------
    eol-style = native

Added: incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/Record.vm
URL: http://svn.apache.org/viewvc/incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/Record.vm?rev=829996&view=auto
==============================================================================
--- incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/Record.vm (added)
+++ incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/Record.vm Mon Oct 26 22:08:18 2009
@@ -0,0 +1,72 @@
+package ${recordPackage};
+
+#if ($table.hasBigDecimalField())
+import java.math.BigDecimal;
+#end
+import java.util.Date;
+
+import ${basePackageName}.${database.className};
+import ${tablePackageName}.${table.className};
+
+/**
+ * Auto-generated class that represents one record (or row) of data from a
+ * database table.  One of these is generated for each table or view in the
+ * database.  The interface defines getters for auto-generated data (e.g. 
+ * primary key, time stamp field for optimistic locking).  It generates both
+ * getter and setter method for all other columns in the table, with the 
+ * exception of foreign key references.
+ *
+ * This class provides protected method that subclasses should use to provide
+ * access to related records.
+ */
+public class ${table.recordClassName} extends BaseRecord<${table.className}> {
+	public ${table.recordClassName}() {
+		super(${database.className}.get().T_${table.tableName});
+	}
+	
+	// Primary key getter
+	public Integer ${table.pkCol.javaAccessorName}() {
+		return (Integer)super.getValue(getDbTable().${table.pkCol.name});
+	}
+	
+	// Access methods for simple attributes
+#foreach($col in $table.simpleCols)
+	public ${col.javaTypeString} ${col.javaAccessorName}() {
+		${col.originalJavaTypeString} ${col.javaName} = (${col.originalJavaTypeString})super.getValue(getDbTable().${col.name});
+		return ${col.returnExpression};
+	}
+	public void ${col.javaMutatorName}(${col.javaTypeString} ${col.javaName}) {
+		super.setValue(getDbTable().${col.name}, ${col.setExpression});
+	}
+#end
+
+	// Optimistic locking getter
+	public ${table.lockingCol.javaTypeString} ${table.lockingCol.javaAccessorName}() {
+		return (${table.lockingCol.javaTypeString})super.getValue(getDbTable().${table.lockingCol.name});		
+	}
+	
+	@Override
+    public boolean equals(Object object) {  
+        if (object == this)  
+            return true;  
+        if ((object == null) || !(object instanceof ${table.recordClassName}))  
+            return false;  
+   
+        final ${table.recordClassName} a = (${table.recordClassName})object;  
+   
+        if (${table.pkCol.javaAccessorName}() != null && a.${table.pkCol.javaAccessorName}() != null) {  
+            return ${table.pkCol.javaAccessorName}().equals(a.${table.pkCol.javaAccessorName}());  
+        }  
+        return false;  
+    }
+    
+    // FK references
+    #foreach($col in $table.fkCols)
+	public Integer ${col.javaAccessorName}() {
+		return (Integer)super.getValue(getDbTable().${col.name});
+	}
+	public void ${col.javaMutatorName}(Integer ${col.javaName}) {
+		super.setValue(getDbTable().${col.name}, ${col.javaName});
+	}
+    #end
+}
\ No newline at end of file

Propchange: incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/Record.vm
------------------------------------------------------------------------------
    eol-style = native

Added: incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/Table.vm
URL: http://svn.apache.org/viewvc/incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/Table.vm?rev=829996&view=auto
==============================================================================
--- incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/Table.vm (added)
+++ incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/Table.vm Mon Oct 26 22:08:18 2009
@@ -0,0 +1,51 @@
+package $tablePackageName;
+
+import org.apache.empire.data.DataType;
+import org.apache.empire.db.DBDatabase;
+import org.apache.empire.db.DBTableColumn;
+
+public class ${table.className} extends ${db.baseTableClassName} {
+	// Primary key column
+	public final DBTableColumn ${table.pkCol.name};
+	
+	// Regular attributes
+#foreach ($col in $table.simpleCols)
+	public final DBTableColumn ${col.name};
+#end
+	
+	// Optimistic locking attribute
+	public final DBTableColumn ${table.lockingCol.name};
+	
+	// Foreign key columns
+#foreach ($col in $table.fkCols)
+	public final DBTableColumn ${col.name};
+#end
+	
+	public ${table.className}(DBDatabase db) {
+		super("${table.tableName}", db);
+		
+		// Primary key column
+		${table.pkCol.name} = super.addColumn("${table.pkCol.name}", DataType.AUTOINC, 0, true);
+		
+		// Regular attributes
+#foreach ($col in $table.simpleCols)
+		${col.name} = super.addColumn("${col.name}", DataType.${col.empireType}, ${col.colSize}, ${col.required}, ${col.defaultValue});
+#end
+
+		// Optimistic locking attribute
+		${table.lockingCol.name} = super.addColumn("${table.lockingCol.name}", DataType.DATETIME, 0, false);
+		
+		// Foreign key columns
+#foreach ($col in $table.fkCols)
+		${col.name} = super.addColumn("${col.name}", DataType.INTEGER, 0, ${col.required});
+#end		
+		// Primary key
+		super.setPrimaryKey(${table.pkCol.name});
+		
+		// Optimistic locking column
+		super.setTimestampColumn(${table.lockingCol.name});
+		
+		// Set cascade delete
+		super.setCascadeDelete(true);		
+	}
+}

Propchange: incubator/empire-db/trunk/empire-db-codegen/src/main/resources/templates/Table.vm
------------------------------------------------------------------------------
    eol-style = native