001: package net.sourceforge.jaxor.generator;
002:
003: import net.sourceforge.jaxor.parser.*;
004: import net.sourceforge.jaxor.util.SystemException;
005: import org.apache.regexp.RE;
006: import org.apache.regexp.RESyntaxException;
007:
008: import java.sql.Connection;
009: import java.sql.DatabaseMetaData;
010: import java.sql.ResultSet;
011: import java.sql.SQLException;
012: import java.util.*;
013:
014: /**
015: * Created By: Mike
016: * Date: Feb 7, 2004
017: * Time: 2:40:31 PM
018: *
019: * Last Checkin: $Author: fspinazzi $
020: * Date: $Date: 2004/02/11 13:50:54 $
021: * Revision: $Revision: 1.6 $
022: */
023: public class MappingMetaData {
024: private Connection _conn;
025: private String _catalog;
026: private String _schema;
027: private Sql2JavaMapping _mapper;
028: private RE tableRE;
029:
030: public MappingMetaData(Connection conn, String catalog,
031: String schema, Sql2JavaMapping mappings, String tableRegExp)
032: throws RESyntaxException {
033: _conn = conn;
034: _catalog = catalog;
035: _schema = schema;
036: _mapper = mappings;
037: tableRE = new RE(tableRegExp);
038: }
039:
040: public Jaxor[] getMapped() {
041: DatabaseMetaData databaseMetaData = getMetaData();
042: ResultSet tables = getTableMeta(databaseMetaData);
043: try {
044: return processMetadata(tables, databaseMetaData);
045: } catch (SQLException e) {
046: throw new SystemException(e);
047: } finally {
048: try {
049: tables.close();
050: } catch (SQLException e) {
051: e.printStackTrace();
052: }
053: }
054: }
055:
056: private ResultSet getTableMeta(DatabaseMetaData databaseMetaData) {
057: try {
058: return databaseMetaData.getTables(getCatalog(),
059: getSchema(), "%", new String[] { "TABLE" });
060: } catch (SQLException e) {
061: throw new SystemException(e);
062: }
063: }
064:
065: private DatabaseMetaData getMetaData() {
066: try {
067: DatabaseMetaData databaseMetaData = _conn.getMetaData();
068: return databaseMetaData;
069: } catch (SQLException e) {
070: throw new SystemException(e);
071: }
072: }
073:
074: private Jaxor[] processMetadata(ResultSet tables,
075: DatabaseMetaData databaseMetaData) throws SQLException {
076:
077: List jaxors = new ArrayList();
078: while (tables.next()) {
079: Jaxor jaxor = new Jaxor();
080: String tableName = tables.getString("TABLE_NAME");
081: if (!shouldProcess(tableName))
082: continue;
083:
084: log("processing table " + tableName);
085: // COLUMNS
086: Map attributes = new HashMap();
087: theColumns(databaseMetaData, tableName, attributes);
088:
089: Entity entity = new Entity(tableName);
090: // PRIMARY KEYS
091: addPrimaryKeysAndRemoveFromAttributes(databaseMetaData,
092: tableName, entity, attributes);
093:
094: // IMPORTED KEYS - more than one table can be referenced
095: addImportedKeysAndRemoveFromAttributes(databaseMetaData,
096: tableName, entity, attributes);
097:
098: // ADD THE (REMAINING) COLUMNS
099: for (Iterator iterator = attributes.keySet().iterator(); iterator
100: .hasNext();) {
101: Attribute attribute = (Attribute) attributes
102: .get(iterator.next());
103: entity.addAttribute(attribute);
104: }
105:
106: if (entity.getPrimaryKey().getKeys().size() == 0) {
107: log("warning: table " + tableName
108: + " doesn't define any primary key");
109: }
110:
111: jaxor.addEntity(entity);
112: jaxors.add(jaxor);
113:
114: }
115: Jaxor[] jaxorsToBeReturned = new Jaxor[jaxors.size()];
116: for (int i = 0; i < jaxors.size(); i++) {
117: Jaxor jaxor = (Jaxor) jaxors.get(i);
118: jaxorsToBeReturned[i] = jaxor;
119: }
120: return jaxorsToBeReturned;
121: }
122:
123: private boolean shouldProcess(String tableName) {
124: return tableRE.match(tableName);
125: }
126:
127: private void addImportedKeysAndRemoveFromAttributes(
128: DatabaseMetaData databaseMetaData, String tableName,
129: Entity entity, Map attributes) throws SQLException {
130: ResultSet importedKeys = databaseMetaData.getImportedKeys(
131: _catalog, _schema, tableName);
132: try {
133: while (importedKeys.next()) {
134: EntityRef entityRef = new EntityRef();
135: entityRef.setTable(importedKeys
136: .getString("PKTABLE_NAME"));
137: Key key = new Key();
138: key.setSource(importedKeys.getString("FKCOLUMN_NAME"));
139: key.setTarget(importedKeys.getString("PKCOLUMN_NAME"));
140: entityRef.addKey(key);
141: entity.addEntityRef(entityRef);
142: attributes.remove(key.getSource());
143: }
144: } finally {
145: importedKeys.close();
146: }
147: }
148:
149: public String getCatalog() {
150: return _catalog;
151: }
152:
153: public String getSchema() {
154: return _schema;
155: }
156:
157: private void addPrimaryKeysAndRemoveFromAttributes(
158: DatabaseMetaData databaseMetaData, String tableName,
159: Entity entity, Map attributes) throws SQLException {
160: ResultSet primaryKeys = databaseMetaData.getPrimaryKeys(
161: getCatalog(), getSchema(), tableName);
162: try {
163: PrimaryKey primaryKey = new PrimaryKey();
164: while (primaryKeys.next()) {
165: final String name = primaryKeys
166: .getString("COLUMN_NAME");
167: final Attribute primaryKeyComponent = (Attribute) attributes
168: .remove(name);
169: primaryKeyComponent.setName(name);
170: primaryKeyComponent.setType(primaryKeyComponent
171: .getType());
172: primaryKey.addAttribute(primaryKeyComponent);
173: }
174: entity.addPrimaryKey(primaryKey);
175: } finally {
176: primaryKeys.close();
177: }
178: }
179:
180: private void theColumns(DatabaseMetaData databaseMetaData,
181: String tableName, Map attributes) throws SQLException {
182: ResultSet columns = databaseMetaData.getColumns(getCatalog(),
183: getSchema(), tableName, "%");
184: try {
185: while (columns.next()) {
186: String columnName = columns.getString("COLUMN_NAME");
187: int dataType = columns.getInt("DATA_TYPE");
188: String dataTypeName = columns.getString("TYPE_NAME");
189: String type = _mapper.getByTypeNameOrCode(dataTypeName,
190: dataType);
191: if (Sql2JavaMapping.UNKNOW_DATA_TYPE.equals(type)) {
192: logUnknownDataType(dataType, dataTypeName,
193: columnName);
194: }
195: boolean nullable = "YES".equals(columns
196: .getString("IS_NULLABLE"));
197: Attribute attribute = new Attribute(columnName, type,
198: nullable);
199: attributes.put(columnName, attribute);
200: }
201: } finally {
202: columns.close();
203: }
204: }
205:
206: protected void logUnknownDataType(int dataType, String dataName,
207: String name) {
208: throw new SystemException("warning: unknown sql data type "
209: + dataType + "(" + dataName + ") column: " + name);
210: }
211:
212: protected void log(String msg) {
213: }
214: }
|