1 7 8 package org.jdesktop.dataset; 9 import java.beans.PropertyChangeEvent ; 10 import java.beans.PropertyChangeListener ; 11 import java.io.ByteArrayInputStream ; 12 import java.io.File ; 13 import java.io.FileInputStream ; 14 import java.io.InputStream ; 15 import java.math.BigDecimal ; 16 import java.util.ArrayList ; 17 import java.util.Collections ; 18 import java.util.Date ; 19 import java.util.HashMap ; 20 import java.util.List ; 21 import java.util.Map ; 22 import javax.xml.parsers.DocumentBuilder ; 23 import javax.xml.parsers.DocumentBuilderFactory ; 24 import javax.xml.xpath.XPath ; 25 import javax.xml.xpath.XPathConstants ; 26 import javax.xml.xpath.XPathFactory ; 27 import org.jdesktop.dataset.event.TableChangeEvent; 28 import org.w3c.dom.Document ; 29 import org.w3c.dom.Node ; 30 import org.w3c.dom.NodeList ; 31 32 36 public class DataSet { 37 private String name; 38 private Map <String ,DataTable> tables = new HashMap <String ,DataTable>(); 39 private Map <String ,DataRelation> relations = new HashMap <String ,DataRelation>(); 40 private Map <String ,DataValue> values = new HashMap <String ,DataValue>(); 41 42 private final class NameChangeListener implements PropertyChangeListener { 43 public void propertyChange(PropertyChangeEvent evt) { 44 Object source = evt.getSource(); 45 if (source instanceof DataTable) { 46 DataTable table = (DataTable)source; 47 tables.remove(evt.getOldValue()); 48 tables.put((String )evt.getNewValue(), table); 49 } else if (source instanceof DataRelation) { 50 DataRelation relation = (DataRelation)source; 51 relations.remove(evt.getOldValue()); 52 relations.put((String )evt.getNewValue(), relation); 53 } else if (source instanceof DataValue) { 54 DataValue value = (DataValue)source; 55 values.remove(evt.getOldValue()); 56 values.put((String )evt.getNewValue(), value); 57 } 58 } 59 } 60 61 private NameChangeListener nameChangeListener = new NameChangeListener(); 62 63 public DataSet() { 64 } 65 66 public DataTable createTable() { 67 DataTable table = new DataTable(this); 68 table.addPropertyChangeListener("name", nameChangeListener); 69 tables.put(table.getName(), table); 70 return table; 71 } 72 73 public DataRelationTable createRelationTable() { 74 DataRelationTable table = new DataRelationTable(this); 75 table.addPropertyChangeListener("name", nameChangeListener); 76 tables.put(table.getName(), table); 77 return table; 78 } 79 80 public DataRelation createRelation() { 81 DataRelation relation = new DataRelation(this); 82 relation.addPropertyChangeListener("name", nameChangeListener); 83 relations.put(relation.getName(), relation); 84 return relation; 85 } 86 87 public DataValue createValue() { 88 DataValue value = new DataValue(this); 89 value.addPropertyChangeListener("name", nameChangeListener); 90 values.put(value.getName(), value); 91 return value; 92 } 93 94 public void dropTable(DataTable table) { 95 dropTable(table.getName()); 96 } 97 98 public void dropTable(String tableName) { 99 tables.remove(tableName).removePropertyChangeListener("name", nameChangeListener); 100 } 101 102 public void dropRelationTable(DataRelationTable table) { 103 dropTable(table.getName()); 104 } 105 106 public void dropRelationTable(String tableName) { 107 dropTable(tableName); 108 } 109 110 public void dropRelation(DataRelation relation) { 111 dropRelation(relation.getName()); 112 } 113 114 public void dropRelation(String relationName) { 115 relations.remove(relationName).removePropertyChangeListener("name", nameChangeListener); 116 } 117 118 public void dropValue(DataValue value) { 119 dropValue(value.getName()); 120 } 121 122 public void dropValue(String valueName) { 123 values.remove(valueName).removePropertyChangeListener("name", nameChangeListener); 124 } 125 126 protected boolean hasElement(String name) { 127 boolean b = relations.containsKey(name); 128 if (!b) { 129 b = tables.containsKey(name); 130 } 131 if (!b) { 132 b = values.containsKey(name); 133 } 134 return b; 135 } 136 137 public List <DataRow> getRows(String path) { 138 if (path == null || path.trim().equals("")) { 139 return Collections.EMPTY_LIST; 140 } 141 142 path = path.trim(); 143 144 String [] steps = path.split("\\."); 146 147 150 List <DataRow> workingSet = null; 152 153 for (String step : steps) { 154 String name = null; 155 String selectorName = null; 156 if (step.contains("[")) { 157 name = step.substring(0, step.indexOf('[')); 158 selectorName = step.substring(step.indexOf('[')+1, step.indexOf(']')); 159 } 160 161 if (workingSet == null) { 162 DataTable table = tables.get(name); 165 if (table == null) { 166 assert false; 167 } 168 workingSet = table.getRows(); 169 if (selectorName != null) { 170 } 172 } else { 173 DataRelation relation = relations.get(name); 175 if (relation == null) { 176 assert false; 177 } 178 workingSet = relation.getRows((DataRow[])workingSet.toArray(new DataRow[workingSet.size()])); 179 if (selectorName != null) { 180 } 182 } 183 } 184 return Collections.unmodifiableList(workingSet); 185 } 186 187 public List <DataRow> filterRows(List <DataRow> rows, DataSelector ds) { 188 List <Integer > indices = ds.getRowIndices(); 189 List <DataRow> results = new ArrayList <DataRow>(indices.size()); 190 for (int index : indices) { 191 results.add(rows.get(index)); 192 } 193 return results; 194 } 195 196 public List <DataColumn> getColumns(String path) { 197 String [] parts = path.split("\\."); 200 assert parts.length == 1 || parts.length == 2; 201 202 DataTable table = tables.get(parts[0]); 203 if (table == null) { 204 DataRelation relation = relations.get(parts[0]); 205 if (relation == null) { 206 return new ArrayList <DataColumn>(); 207 } else { 208 table = relation.getChildColumn().getTable(); 209 } 210 } 211 212 if (parts.length == 1) { 213 return table.getColumns(); 214 } else { 215 List <DataColumn> results = new ArrayList <DataColumn>(); 216 results.add(table.getColumn(parts[1])); 217 return Collections.unmodifiableList(results); 218 } 219 } 220 221 public DataTable getTable(String tableName) { 222 return tables.get(tableName); 223 } 224 225 public DataRelationTable getRelationTable(String name) { 226 return (DataRelationTable)tables.get(name); 227 } 228 229 public void load() { 230 for (DataTable table : tables.values()) { 231 if (!(table instanceof DataRelationTable)) { 232 table.load(); 233 } 234 } 235 } 236 237 240 public static DataSet createFromSchema(String schema) { 241 DataSet ds = new DataSet(); 242 try { 244 DocumentBuilder db = DocumentBuilderFactory.newInstance().newDocumentBuilder(); 245 Document dom = db.parse(new ByteArrayInputStream (schema.getBytes())); 246 247 XPath xpath = XPathFactory.newInstance().newXPath(); 249 ds.name = xpath.evaluate("/schema/@id", dom); 250 251 String expression = "/schema/element[@name='" + ds.name + "']"; 254 NodeList nodes = (NodeList )xpath.evaluate(expression, dom, XPathConstants.NODESET); 255 if (nodes != null && nodes.getLength() > 0) { 256 Node dataSetNode = nodes.item(0); 257 NodeList tableNodes = (NodeList )xpath.evaluate("complexType/choice/element", dataSetNode, XPathConstants.NODESET); 259 for (int i=0; i<tableNodes.getLength(); i++) { 260 Node tableNode = tableNodes.item(i); 261 DataTable table = ds.createTable(); 262 table.setName(xpath.evaluate("@name", tableNode)); 263 NodeList columnNodes = (NodeList )xpath.evaluate("complexType/sequence/element", tableNode, XPathConstants.NODESET); 265 for (int j=0; j<columnNodes.getLength(); j++) { 266 Node colNode = columnNodes.item(j); 267 DataColumn col = table.createColumn(xpath.evaluate("@name", colNode)); 268 String minOccurs = xpath.evaluate("@minOccurs", colNode); 270 if (minOccurs.equals("")) { 271 col.setRequired(true); 272 } 273 274 String defaultValue = xpath.evaluate("@default", colNode); 275 String classType = xpath.evaluate("@type", colNode); 276 if (classType.equals("xs:string")) { 277 col.setType(String .class); 278 if (!defaultValue.equals("")) { 279 col.setDefaultValue(defaultValue); 280 } 281 } else if (classType.equals("xs:decimal")) { 282 col.setType(BigDecimal .class); 283 if (!defaultValue.equals("")) { 284 col.setDefaultValue(new BigDecimal (defaultValue)); 285 } 286 } else if (classType.equals("xs:integer") || classType.equals("xs:int")) { 287 col.setType(Integer .class); 288 if (!defaultValue.equals("")) { 289 col.setDefaultValue(new Integer (defaultValue)); 290 } 291 } else if (classType.equals("xs:boolean")) { 292 col.setType(Boolean .class); 293 if (!defaultValue.equals("")) { 294 col.setDefaultValue(Boolean.parseBoolean(defaultValue)); 295 } 296 } else if (classType.equals("xs:date") || classType.equals("xs:time") || classType.equals("xs.dateTime")) { 297 col.setType(Date .class); 298 if (!defaultValue.equals("")) { 299 col.setDefaultValue(new Date (Date.parse(defaultValue))); 300 } 301 } else if (classType.equals("xs:unsignedByte")) { 302 col.setType(Byte .class); 303 if (!defaultValue.equals("")) { 304 col.setDefaultValue(new Byte (defaultValue)); 305 } 306 } else { 307 System.err.println("unexpected classType: '" + classType + "'"); 308 } 309 } 310 } 311 } 312 } catch (Exception e) { 313 e.printStackTrace(); 314 } 315 return ds; 316 } 317 318 321 public String getSchema() { 322 StringBuilder buffer = new StringBuilder (); 323 buffer.append("<?xml version=\"1.0\" standalone=\"yes\" ?>\n"); 324 buffer.append("<xs:schema id=\"DataSet2\" targetNamespace=\"http://www.tempuri.org/DataSet2.xsd\" xmlns:mstns=\"http://www.tempuri.org/DataSet2.xsd\" " + 325 "xmlns=\"http://www.tempuri.org/DataSet2.xsd\" xmlns:xs=\"http://www.w3.org/2001/XMLSchema\" " + 326 "xmlns:msdata=\"urn:schemas-microsoft-com:xml-msdata\" attributeFormDefault=\"qualified\" elementFormDefault=\"qualified\">\n"); 327 buffer.append("\t<xs:element name=\""); 328 buffer.append(name); 329 buffer.append(" msdata:IsDataSet=\"true\">\n"); 330 buffer.append("\t\t<xs:complexType>\n"); 331 buffer.append("\t\t\t<xs:choice maxOccurs=\"unbounded\">\n"); 332 for (DataTable table : tables.values()) { 333 buffer.append("\t\t\t\t<xs:element name=\""); 334 buffer.append(table.getName()); 335 buffer.append("\">\n"); 336 buffer.append("\t\t\t\t\t<xs:complexType>\n"); 337 buffer.append("\t\t\t\t\t\t<xs:sequence>\n"); 338 for (DataColumn col : table.getColumns()) { 339 buffer.append("\t\t\t\t\t\t\t<xs:element name=\""); 340 buffer.append(col.getName()); 341 buffer.append("\" type=\""); 342 if (col.getType() == String .class) { 343 buffer.append("xs:string"); 344 } else if (col.getType() == BigDecimal .class) { 345 buffer.append("xs:decimal"); 346 } else if (col.getType() == Integer .class) { 347 buffer.append("xs:integer"); 348 } else if (col.getType() == Boolean .class) { 349 buffer.append("xs:boolean"); 350 } else if (col.getType() == Date .class) { 351 buffer.append("xs:dateTime"); 352 } else if (col.getType() == Byte .class) { 353 buffer.append("xs:unsignedByte"); 354 } 355 if (col.getDefaultValue() != null) { 356 buffer.append("\" default=\""); 357 buffer.append(col.getDefaultValue()); 358 } 359 if (!col.isRequired()) { 360 buffer.append("\" minOccurs=\"0"); 361 } 362 buffer.append("\" />\n"); 363 } 364 buffer.append("\t\t\t\t\t\t</xs:sequence>\n"); 365 buffer.append("\t\t\t\t\t</xs:complexType>\n"); 366 buffer.append("\t\t\t\t</xs:element>\n"); 367 } 368 buffer.append("\t\t\t</xs:choice>\n"); 369 buffer.append("\t\t</xs:complexType>\n"); 370 371 373 buffer.append("\t</xs:element>\n"); 375 buffer.append("</xs:schema>\n"); 376 377 return buffer.toString(); 378 } 379 380 public static DataSet createFromSchema(File f) { 381 String schema = ""; 382 try { 383 FileInputStream fis = new FileInputStream (f); 384 DataSet ds = createFromSchema(fis); 385 fis.close(); 386 return ds; 387 } catch (Exception e) { 388 e.printStackTrace(); 389 return null; 390 } 391 } 392 393 public static DataSet createFromSchema(InputStream is) { 394 String schema = ""; 395 try { 396 StringBuilder builder = new StringBuilder (); 397 byte[] bytes = new byte[4096]; 398 int length = -1; 399 while ((length = is.read(bytes)) != -1) { 400 builder.append(new String (bytes, 0, length)); 401 } 402 schema = builder.toString(); 403 return createFromSchema(schema); 404 } catch (Exception e) { 405 e.printStackTrace(); 406 return null; 407 } 408 } 409 410 public void readXml(File f) { 411 String xml = ""; 412 try { 413 FileInputStream fis = new FileInputStream (f); 414 readXml(fis); 415 fis.close(); 416 } catch (Exception e) { 417 e.printStackTrace(); 418 } 419 } 420 421 public void readXml(InputStream is) { 422 String xml = ""; 423 try { 424 StringBuilder builder = new StringBuilder (); 425 byte[] bytes = new byte[4096]; 426 int length = -1; 427 while ((length = is.read(bytes)) != -1) { 428 builder.append(new String (bytes, 0, length)); 429 } 430 xml = builder.toString(); 431 readXml(xml); 432 } catch (Exception e) { 433 e.printStackTrace(); 434 } 435 } 436 437 public void readXml(String xml) { 438 440 try { 441 DocumentBuilder db = DocumentBuilderFactory.newInstance().newDocumentBuilder(); 442 Document dom = db.parse(new ByteArrayInputStream (xml.getBytes())); 443 444 XPath xpath = XPathFactory.newInstance().newXPath(); 446 447 for (DataTable table : tables.values()) { 449 if (!(table instanceof DataRelationTable)) { 450 table.clear(); 452 NodeList nodes = (NodeList )xpath.evaluate("/" + name + "/" + table.getName(), dom, XPathConstants.NODESET); 454 for (int i=0; i<nodes.getLength(); i++) { 456 Node rowNode = nodes.item(i); 458 DataRow row = table.appendRowNoEvent(); 459 NodeList cols = rowNode.getChildNodes(); 460 for (int j=0; j<cols.getLength(); j++) { 461 Node colNode = cols.item(j); 462 if (colNode.getNodeType() == Node.ELEMENT_NODE) { 463 System.out.println(colNode.getNodeName() + "=" + colNode.getTextContent()); 466 row.setValue(colNode.getNodeName(), colNode.getTextContent()); 467 } 468 } 469 row.setStatus(DataRow.DataRowStatus.UNCHANGED); 470 } 471 table.fireDataTableChanged(new TableChangeEvent(table)); 472 } 473 } 474 } catch (Exception e) { 475 e.printStackTrace(); 476 } 477 } 478 479 public String writeXml() { 480 StringBuilder builder = new StringBuilder (); 481 builder.append("<?xml version=\"1.0\" ?>\n"); 482 builder.append("<"); 483 builder.append(name); 484 builder.append(">\n"); 485 for (DataTable table : tables.values()) { 486 if (!(table instanceof DataRelationTable)) { 487 for (DataRow row : table.rows) { 488 builder.append("\t<"); 489 builder.append(table.getName()); 490 builder.append(">\n"); 491 492 for (DataColumn col : table.columns.values()) { 493 builder.append("\t\t<"); 494 builder.append(col.getName()); 495 builder.append(">"); 496 builder.append(row.getValue(col)); 497 builder.append("</"); 498 builder.append(col.getName()); 499 builder.append(">\n"); 500 } 501 502 builder.append("\t</"); 503 builder.append(table.getName()); 504 builder.append(">\n"); 505 } 506 } 507 } 508 builder.append("</"); 509 builder.append(name); 510 builder.append(">"); 511 512 return builder.toString(); 513 } 514 515 public static void main(String [] args) { 516 DataSet ds = createFromSchema(new File ("/home/rb156199/dataset.xsd")); 517 System.out.println("DataSet: " + ds.name); 518 for (DataTable table : ds.tables.values()) { 519 System.out.println("\tDataTable: " + table.getName()); 520 for (DataColumn col : table.getColumns()) { 521 System.out.println("\t\tDataColumn: " + col.getName()); 522 } 523 } 524 525 System.out.println(ds.getSchema()); 526 } 527 } | Popular Tags |