1 22 23 package org.xquark.extractor.metadata; 24 25 import java.sql.*; 26 import java.util.*; 27 28 import org.apache.commons.logging.Log; 29 import org.apache.commons.logging.LogFactory; 30 import org.xquark.extractor.common.MessageLibrary; 31 import org.xquark.extractor.common.MetaDataException; 32 import org.xquark.extractor.runtime.Selection; 33 import org.xquark.jdbc.typing.ColumnMetaData; 34 import org.xquark.jdbc.typing.DBMSInfo; 35 import org.xquark.jdbc.typing.JDBCProperties; 36 37 42 public abstract class Loader { 43 44 private static final String RCSRevision = "$Revision: 1.24 $"; 45 private static final String RCSName = "$Name: $"; 46 47 private static Log log = LogFactory.getLog(Loader.class); 48 49 50 public Properties _tableMap = new Properties(); 51 52 protected Connection _connection; 53 protected DatabaseMetaData _databaseMetaData; 54 protected DBMSInfo _dbmsInfo; 55 protected HashSet _nameSpaces = new HashSet(); 56 protected QNameEncoder _encoder = null; 57 58 public Loader(Connection connection, DBMSInfo dbmsInfo, QNameEncoder encoder) throws SQLException { 59 _connection = connection; 60 _databaseMetaData = connection.getMetaData(); 61 _dbmsInfo = dbmsInfo; 62 _encoder = encoder; 63 } 64 65 73 public Site loadSite(Selection selection, JDBCProperties JDBCprop) throws MetaDataException { 74 75 Site retVal = new Site(null); 76 List children = new ArrayList(); 77 List subSelections = new ArrayList(); 78 ResultSet resultSet = null; 79 String name = null; 80 81 _nameSpaces.clear(); 82 83 try { 84 String defCatalog = getDefaultCatalog(); 85 86 if (null == selection) { 87 selection = new Selection(null, null, Selection.INCLUDES, new HashMap()); 88 } 89 90 if (selection.noSubElementDef()) { 91 Selection catalogSel = new Selection(defCatalog, null, Selection.INCLUDES, new HashMap()); 92 selection.addToMap(defCatalog, catalogSel); 93 } 94 95 96 resultSet = _databaseMetaData.getCatalogs(); 97 Selection subSelection = null; 98 while (resultSet.next()) { 99 name = resultSet.getString("TABLE_CAT"); 100 subSelection = selection.includesSubElement(name); 101 if (subSelection != null) { 102 children.add(name); 106 subSelections.add(subSelection); 107 } 108 } 109 resultSet.close(); 110 111 112 subSelection = selection.includesSubElement(null); 113 if (subSelection != null) { 114 if (defCatalog == null) { 115 children.add(null); 116 subSelections.add(subSelection); 117 } else { 118 children.add(defCatalog); 119 subSelection.setNameForDefault(defCatalog); 120 subSelections.add(subSelection); 121 } 122 } 123 124 if (children.isEmpty()) { 125 throw new MetaDataException("Wrong catalog configuration specification. Check your configuration file."); 126 } 127 128 129 for (int i = 0; i < children.size(); i++) { 130 String child = (String ) children.get(i); 131 subSelection = (Selection) subSelections.get(i); 132 retVal.addChild(loadCatalog(child, subSelection, JDBCprop)); 133 } 134 135 } catch (SQLException ex) { 136 throw new MetaDataException(ex.getMessage(), ex); 137 } 138 return retVal; 139 } 140 141 150 protected Catalog loadCatalog(String catalogName, Selection selection, JDBCProperties JDBCprop) throws MetaDataException { 151 153 List children = new ArrayList(); 154 List subSelections = new ArrayList(); 155 ResultSet resultSet = null; 156 String name = null; 157 158 159 Catalog retVal = null; 160 if (catalogName == null || catalogName.length() == 0) 161 retVal = new Catalog(null); 162 else 163 retVal = new Catalog(catalogName); 164 165 166 try { 167 String defSchema = getDefaultSchema(); 168 169 if (selection.noSubElementDef()) { 170 Selection schemaSel = new Selection(defSchema, null, Selection.INCLUDES, new HashMap()); 171 selection.addToMap(defSchema, schemaSel); 172 } 173 174 resultSet = _databaseMetaData.getSchemas(); 175 Selection subSelection = null; 176 while (resultSet.next()) { 177 name = resultSet.getString("TABLE_SCHEM"); 178 subSelection = selection.includesSubElement(name); 179 if (subSelection != null) { 180 String targetNameSpace = subSelection.getTargetNamespace(); 181 if (_nameSpaces.contains(targetNameSpace)) 183 throw new MetaDataException("Same target namespace : [" + targetNameSpace + "] used twice"); 184 _nameSpaces.add(targetNameSpace); 185 children.add(name); 186 subSelections.add(subSelection); 187 } 188 } 189 resultSet.close(); 190 191 192 subSelection = selection.includesSubElement(null); 193 if (subSelection != null) { 194 if (defSchema == null) { 195 children.add(null); 196 subSelections.add(subSelection); 197 } else { 198 children.add(defSchema); 199 subSelection.setNameForDefault(defSchema); 200 subSelections.add(subSelection); 201 } 202 } 203 204 if (children.isEmpty()) { 205 throw new MetaDataException("Wrong schema configuration specification. Check your configuration file."); 206 } 207 208 209 for (int i = 0; i < children.size(); i++) { 210 String child = (String ) children.get(i); 211 subSelection = (Selection) subSelections.get(i); 212 retVal.addChild(loadSchema(catalogName, child, subSelection, JDBCprop)); 213 } 214 } catch (SQLException ex) { 215 throw new MetaDataException(ex.getMessage(), ex); 216 } 217 218 return retVal; 220 221 } 222 223 234 protected Schema loadSchema(String catalogName, String schemaName, Selection selection, JDBCProperties JDBCprop) throws MetaDataException { 235 237 List children = new ArrayList(); 238 List subSelections = new ArrayList(); 239 NamedNode catalog = null; 240 ResultSet resultSet = null; 241 String name = null; 242 _nameSpaces.clear(); 243 String alias = null; 244 245 246 Schema retVal = new Schema(schemaName); 247 if (selection != null) { 248 retVal.setTargetNamespace(selection.getTargetNamespace()); 249 retVal.setElementFormDefault(selection.getElementFormDefault()); 250 } 251 252 253 try { 254 String [] tableTypes = { "TABLE", "VIEW", "SYNONYM" }; 255 String tableType = null; 256 resultSet = _databaseMetaData.getTables(catalogName, schemaName, null, tableTypes); 257 258 if (selection == null || selection.noSubElementDef()) { 259 260 while (resultSet.next()) { 261 tableType = resultSet.getString("TABLE_TYPE"); 262 name = resultSet.getString("TABLE_NAME"); 263 alias = _encoder.encode(name); 264 if (!Selection.verifyName(alias)) { 265 log.warn(MessageLibrary.getMessage("C_INV_NCNAME", alias)); 266 log.warn(MessageLibrary.getMessage("M_OBJ_N_LOADED", tableType + " " + schemaName + "." + name)); 267 continue; } 269 270 if (tableType.equalsIgnoreCase("TABLE")) { 271 children.add(new Relation(name, alias, Table.TABLE)); 272 subSelections.add(null); 273 } else if (tableType.equalsIgnoreCase("VIEW")) { 274 children.add(new Relation(name, alias, Table.VIEW)); 275 subSelections.add(null); 276 } else if (tableType.equalsIgnoreCase("SYNONYM")) { 277 children.add(new Relation(name, alias, Table.SYNONYM)); 278 subSelections.add(null); 279 } else { 280 log.warn(MessageLibrary.getMessage("M_OBJ_N_LOADED", tableType + " " + schemaName + "." + name)); 281 } 282 } 283 resultSet.close(); 284 } else { 285 286 Selection subSelection = null; 287 while (resultSet.next()) { 288 name = resultSet.getString("TABLE_NAME"); 289 subSelection = selection.includesSubElement(name); 290 if (subSelection != null) { 291 tableType = resultSet.getString("TABLE_TYPE"); 292 alias = subSelection.getAlias(); 293 if (alias == null) { 294 alias = _encoder.encode(name); 295 if (!Selection.verifyName(alias)) { 296 log.warn(MessageLibrary.getMessage("C_INV_NCNAME", alias)); 297 log.warn(MessageLibrary.getMessage("M_OBJ_N_LOADED", tableType + " " + schemaName + "." + name)); 298 continue; } 300 } 301 302 if (tableType.equalsIgnoreCase("TABLE")) { 303 children.add(new Relation(name, alias, Table.TABLE)); 304 subSelections.add(subSelection); 305 } else if (tableType.equalsIgnoreCase("VIEW")) { 306 children.add(new Relation(name, alias, Table.VIEW)); 307 subSelections.add(subSelection); 308 } else if (tableType.equalsIgnoreCase("SYNONYM")) { 309 children.add(new Relation(name, alias, Table.SYNONYM)); 310 subSelections.add(subSelection); 311 } else { 312 log.warn(MessageLibrary.getMessage("M_OBJ_N_LOADED", tableType + " " + schemaName + "." + name)); 313 } 314 } 315 } 316 resultSet.close(); 317 } 318 319 String path = null; 321 if (null != catalogName) 322 path = catalogName; 323 if (schemaName != null) 324 if (path == null) 325 path = schemaName; 326 else 327 path += '.' + schemaName; 328 329 String encodedName = null; 330 331 332 for (int i = 0; i < children.size(); i++) { 333 Relation child = ((Relation) children.get(i)); 334 Selection subSelection = (Selection) subSelections.get(i); 335 336 putTable(path, child.alias, child.name); 338 NamedNode childNode = null; 339 if (Table.TABLE == child.type) { 340 childNode = loadTable(catalogName, schemaName, child.name, child.alias, subSelection, JDBCprop); 341 if (childNode != null) { 342 loadKeys(catalogName, schemaName, (Table) childNode, subSelection); 343 } 344 } else { 345 childNode = loadTable(catalogName, schemaName, child.name, child.alias, subSelection, JDBCprop); 346 } 347 if (childNode != null) { 348 retVal.addChild(childNode); 349 } 350 } 351 } catch (SQLException ex) { 352 throw new MetaDataException(ex.getMessage(), ex); 353 } 354 355 return retVal; 357 } 358 359 371 protected Table loadTable(String catalogName, String schemaName, String origTableName, String tableName, Selection selection, JDBCProperties JDBCprop) throws MetaDataException { 372 374 375 Table retTable = new Table(origTableName, tableName); 376 retTable.setType(Table.TABLE); 377 378 379 List columnsMeta = null; 380 try { 381 columnsMeta = _dbmsInfo.getTableMetadata(catalogName, schemaName, origTableName, _connection, JDBCprop); 382 } catch (SQLException ex) { 383 log.error(ex); 384 log.warn(MessageLibrary.getMessage("M_OBJ_N_LOADED", "Table : " + schemaName + "." + origTableName)); 385 return null; 387 } 388 389 390 Attribute attribute = null; 391 ColumnMetaData column = null; 392 Selection subSelection = null; 393 String alias = null; 394 List pkAttributes = new ArrayList(); 395 boolean currentColumnIsInPK = false; 397 398 400 String path = null; 401 if (null != catalogName) 402 path = catalogName + '.' + schemaName + '.' + tableName; 403 else 404 path = schemaName + '.' + tableName; 405 406 for (int i = 0; i < columnsMeta.size(); i++) { 407 column = (ColumnMetaData) columnsMeta.get(i); 408 409 currentColumnIsInPK = false; 410 alias = null; 411 412 if (selection == null || selection.noSubElementDef()) { 413 alias = _encoder.encode(column.getColumnName()); 414 if (!Selection.verifyName(alias)) { 415 log.warn(MessageLibrary.getMessage("C_INV_NCNAME", alias)); 416 log.warn(MessageLibrary.getMessage("M_OBJ_N_LOADED", schemaName + "." + origTableName + "." + column.getColumnName())); 417 continue; } 419 } else { 420 subSelection = selection.includesSubElement(column.getColumnName()); 421 if (subSelection == null) { 422 continue; } else { 424 alias = subSelection.getAlias(); 425 if (alias == null) { 426 alias = _encoder.encode(column.getColumnName()); 427 if (!Selection.verifyName(alias)) { 428 log.warn(MessageLibrary.getMessage("C_INV_NCNAME", alias)); 429 log.warn(MessageLibrary.getMessage("M_OBJ_N_LOADED", schemaName + "." + origTableName + "." + column.getColumnName())); 430 continue; 431 } 432 } 433 if (subSelection.getPKColumn()) { 434 currentColumnIsInPK = true; 435 } 436 } 437 } 438 putAttribute(path, alias, column.getColumnName()); 440 441 ExtractorMappingInfo mappingInfo = null; 442 try { 443 mappingInfo = new ExtractorMappingInfo(column, _dbmsInfo.getTypeMap()); 444 } catch (MetaDataException e) { 445 MessageLibrary.getMessage("M_SUP_DATATYPE", new String [] { column.getType().getNativeType(), column.getTableName(), column.getColumnName()}); 446 continue; 447 } 448 449 attribute = new Attribute(column.getColumnName(), alias); 450 attribute.setMappingInfo(mappingInfo); 451 attribute.setNullable(column.isNullable()); 452 453 454 retTable.addChild(attribute); 455 456 460 if (currentColumnIsInPK) { 462 pkAttributes.add(attribute); 463 } 464 } 465 466 467 if (!pkAttributes.isEmpty()) { 468 retTable.addKey(pkAttributes); 469 } 470 471 return retTable; 473 } 474 475 483 protected void loadKeys(String catalogName, String schemaName, Table table, Selection selection) throws MetaDataException { 484 486 try { 487 String column_name = null; 490 String alias = null; 491 Selection subSelection = null; 492 Attribute attribute = null; 493 List key = new ArrayList(); 494 495 ResultSet resultSet = _databaseMetaData.getPrimaryKeys(catalogName, schemaName, table.getName()); 496 497 String path = null; 498 if (null != catalogName) { 499 path = catalogName + '.' + schemaName + '.' + table.getName(); 500 } else { 501 path = schemaName + '.' + table.getName(); 502 } 503 504 505 while (resultSet.next()) { 506 column_name = resultSet.getString("COLUMN_NAME"); 507 508 509 alias = null; 510 if (selection == null || selection.noSubElementDef()) { 511 alias = _encoder.encode(column_name); 512 } else { 513 subSelection = selection.includesSubElement(column_name); 514 if (subSelection == null) { 515 alias = _encoder.encode(column_name); 516 } else { 517 alias = subSelection.getAlias(); 518 if (null == alias) { 519 alias = _encoder.encode(column_name); 520 } 521 } 522 } 523 524 526 attribute = (Attribute) table.findChild(column_name); 527 if (attribute == null) { 528 putAttribute(path, alias, column_name); 529 attribute = new Attribute(column_name, alias); 530 } 531 key.add(attribute); 532 } 533 resultSet.close(); 534 535 536 if (!key.isEmpty()) { 537 table.addKey(key); 538 } 539 } catch (SQLException ex) { 540 throw new MetaDataException(ex.getMessage()); 541 } 542 } 544 545 552 protected void putTable(String path, String encodedTableName, String originalName) throws MetaDataException { 553 String key = null; 554 key = path + '.' + encodedTableName; 555 556 Object value = null; 557 value = _tableMap.getProperty(key); 558 if (null == value) { 559 _tableMap.setProperty(key, originalName); 560 } else { 561 throw new MetaDataException(MessageLibrary.getMessage("M_NAME_CONF", key, originalName)); 562 } 563 } 564 565 572 protected void putAttribute(String path, String encodedAttributeName, String originalName) throws MetaDataException { 573 String key = null; 574 key = path + '.' + encodedAttributeName; 575 576 Object value = null; 577 value = _tableMap.getProperty(key); 578 if (null == value) { 579 _tableMap.setProperty(key, originalName); 580 } else { 581 throw new MetaDataException(MessageLibrary.getMessage("M_NAME_CONF", key, originalName)); 582 } 583 } 584 585 590 protected String getDefaultCatalog() throws SQLException { 591 return _connection.getCatalog(); 592 } 593 594 599 protected String getDefaultSchema() throws SQLException { 600 return _databaseMetaData.getUserName(); 601 } 602 603 606 class Relation { 607 608 public String name; 609 public String alias; 610 public int type; 611 612 public Relation(String name, String alias, int type) { 613 this.name = name; 614 this.alias = alias; 615 this.type = type; 616 } 617 618 public Relation(String name, int type) { 619 this.name = name; 620 this.type = type; 621 this.alias = name; 622 } 623 } 624 } 625 | Popular Tags |