Revision 2074
Added by Matt Jones over 20 years ago
test/query.xml | ||
---|---|---|
1 | 1 |
<?xml version="1.0"?> |
2 | 2 |
<pathquery version="1.2"> |
3 | 3 |
<querytitle>Untitled-Search-1</querytitle> |
4 |
<returndoctype>eml://ecoinformatics.org//eml-2.0.0</returndoctype> |
|
4 | 5 |
<returndoctype>-//ecoinformatics.org//eml-dataset-2.0.0beta4//EN</returndoctype> |
5 | 6 |
<returndoctype>-//ecoinformatics.org//eml-dataset-2.0.0beta6//EN</returndoctype> |
6 | 7 |
<returndoctype>-//NCEAS//eml-dataset-2.0//EN</returndoctype> |
... | ... | |
8 | 9 |
<returnfield>dataset/title</returnfield> |
9 | 10 |
<returnfield>originator/individualName/surName</returnfield> |
10 | 11 |
<returnfield>keyword</returnfield> |
12 |
<returnfield>/eml/@packageId</returnfield> |
|
13 |
<returnfield>/eml/dataset/access/@authSystem</returnfield> |
|
14 |
<returnfield>/eml/dataset/access/@order</returnfield> |
|
11 | 15 |
<querygroup operator="INTERSECT"> |
12 | 16 |
<querygroup operator="UNION"> |
13 | 17 |
<querygroup operator="UNION"> |
test/edu/ucsb/nceas/metacattest/QuerySpecificationTest.java | ||
---|---|---|
87 | 87 |
TestSuite suite = new TestSuite(); |
88 | 88 |
suite.addTest(new QuerySpecificationTest("testPrintSQL")); |
89 | 89 |
suite.addTest(new QuerySpecificationTest("testPrintExtendedSQL")); |
90 |
suite.addTest(new QuerySpecificationTest("testAttributeSQL")); |
|
90 | 91 |
return suite; |
91 | 92 |
} |
92 | 93 |
|
... | ... | |
96 | 97 |
public void testPrintSQL() |
97 | 98 |
{ |
98 | 99 |
try { |
99 |
System.out.println("----------------------"); |
|
100 |
System.out.println("---- SQL ------------------");
|
|
100 | 101 |
QuerySpecification qspec = new QuerySpecification(xml, |
101 | 102 |
MetaCatUtil.getOption("saxparser"), |
102 | 103 |
MetaCatUtil.getOption("accNumberSeparator")); |
... | ... | |
112 | 113 |
public void testPrintExtendedSQL() |
113 | 114 |
{ |
114 | 115 |
try { |
115 |
System.out.println("----------------------"); |
|
116 |
System.out.println("---- EXT SQL ------------------");
|
|
116 | 117 |
Hashtable controlPairs = new Hashtable(); |
117 | 118 |
QuerySpecification qspec = new QuerySpecification(xml, |
118 | 119 |
MetaCatUtil.getOption("saxparser"), |
119 | 120 |
MetaCatUtil.getOption("accNumberSeparator")); |
120 | 121 |
System.out.println( |
121 |
qspec.printExtendedSQL("'obfs.45337', 'obfs.45338', 'obfs.45346'", |
|
122 |
qspec.printExtendedSQL( |
|
123 |
"'obfs.45337', 'obfs.45338', 'obfs.45346'", |
|
122 | 124 |
controlPairs, false)); |
123 | 125 |
} catch (IOException e) { |
124 | 126 |
fail(e.getMessage()); |
125 | 127 |
} |
126 | 128 |
} |
127 | 129 |
|
130 |
/** |
|
131 |
* Print the extended SQL for a result set. |
|
132 |
*/ |
|
133 |
public void testAttributeSQL() |
|
134 |
{ |
|
135 |
try { |
|
136 |
System.out.println("---- ATT SQL ------------------"); |
|
137 |
Hashtable controlPairs = new Hashtable(); |
|
138 |
QuerySpecification qspec = new QuerySpecification(xml, |
|
139 |
MetaCatUtil.getOption("saxparser"), |
|
140 |
MetaCatUtil.getOption("accNumberSeparator")); |
|
141 |
System.out.println( |
|
142 |
qspec.printAttributeQuery( |
|
143 |
"'obfs.45337', 'obfs.45338', 'obfs.45346'", false)); |
|
144 |
} catch (IOException e) { |
|
145 |
fail(e.getMessage()); |
|
146 |
} |
|
147 |
} |
|
128 | 148 |
} |
lib/metacat.properties | ||
---|---|---|
60 | 60 |
datafilesizelimit=1000 |
61 | 61 |
defaultcontenttype=@defaultcontenttype@ |
62 | 62 |
query.ignored.params=enableediting,foo |
63 |
usexmlindex=false |
src/edu/ucsb/nceas/metacat/QuerySpecification.java | ||
---|---|---|
670 | 670 |
countAttributeReturnField++; |
671 | 671 |
hasAttributeReturnField = true; |
672 | 672 |
containsExtendedSQL = true; |
673 |
|
|
674 | 673 |
} |
675 | 674 |
} |
676 | 675 |
|
... | ... | |
933 | 932 |
self.append(")"); |
934 | 933 |
} |
935 | 934 |
} |
936 |
|
|
935 |
|
|
937 | 936 |
/** |
938 |
* This method prints sql based upon the returnfield tag in the pathquery |
|
939 |
* document has an attribute. This allows for customization of the returned |
|
940 |
* fields. |
|
937 |
* This method prints sql that finds the values of attributes in the xml |
|
938 |
* documents based upon the whether the returnfield tag in the pathquery |
|
939 |
* document has an attribute symbol (@). This allows for customization of |
|
940 |
* the returned fields. |
|
941 | 941 |
* |
942 |
* @param doclist |
|
943 |
* the list of document ids to search by |
|
942 |
* @param doclist the list of document ids to search |
|
943 |
* @param useXMLIndex a boolean flag indicating whether to search using |
|
944 |
* xml_index |
|
944 | 945 |
*/ |
946 |
public String printAttributeQuery(String doclist, boolean useXMLIndex) |
|
947 |
{ |
|
948 |
if (useXMLIndex) { |
|
949 |
return printAttributeQuery(doclist); |
|
950 |
} else { |
|
951 |
StringBuffer self = new StringBuffer(); |
|
952 |
boolean firstfield = true; |
|
953 |
//put the returnfields attributes into the query |
|
954 |
//the for loop allows for multiple fields and attributes |
|
955 |
Enumeration returnAttributes = attributeReturnList.elements(); |
|
956 |
while (returnAttributes.hasMoreElements()) { |
|
957 |
Vector currentVector = (Vector) returnAttributes.nextElement(); |
|
958 |
String returnPath = (String) currentVector.elementAt(0); |
|
959 |
String attributeName = (String) currentVector.elementAt(1); |
|
960 |
if (firstfield) { |
|
961 |
firstfield = false; |
|
962 |
self.append("("); |
|
963 |
} else { |
|
964 |
self.append(" UNION ("); |
|
965 |
} |
|
966 |
self.append("select xml_nodes.docid, '"); |
|
967 |
self.append(returnPath); |
|
968 |
self.append("' as path, xml_nodes.nodedata, xml_nodes.nodename "); |
|
969 |
self.append("from xml_nodes, xml_documents "); |
|
970 |
self.append("where parentnodeid IN "); |
|
971 |
self.append(QueryTerm.useNestedStatements(returnPath)); |
|
972 |
self.append(" AND xml_nodes.nodename like '"); |
|
973 |
self.append(attributeName); |
|
974 |
self.append("' AND xml_nodes.docid in ("); |
|
975 |
self.append(doclist); |
|
976 |
self.append(") AND xml_nodes.nodetype = 'ATTRIBUTE'"); |
|
977 |
self.append(" AND xml_nodes.rootnodeid = xml_documents.rootnodeid)"); |
|
978 |
} |
|
979 |
|
|
980 |
MetaCatUtil.debugMessage("Attribute query: " + self.toString(), 30); |
|
981 |
|
|
982 |
return self.toString(); |
|
983 |
} |
|
984 |
} |
|
985 |
|
|
986 |
/** |
|
987 |
* This method prints sql that finds the values of attributes in the xml |
|
988 |
* documents based upon the whether the returnfield tag in the pathquery |
|
989 |
* document has an attribute symbol (@). This allows for customization of |
|
990 |
* the returned fields. |
|
991 |
* |
|
992 |
* @param doclist the list of document ids to search |
|
993 |
*/ |
|
945 | 994 |
public String printAttributeQuery(String doclist) |
946 | 995 |
{ |
947 | 996 |
StringBuffer self = new StringBuffer(); |
... | ... | |
974 | 1023 |
} |
975 | 1024 |
self.append(") AND xml_nodes.docid in ("); |
976 | 1025 |
self.append(doclist); |
977 |
self.append(")"); |
|
978 |
self.append(" AND xml_nodes.nodetype = 'ATTRIBUTE'"); |
|
1026 |
self.append(") AND xml_nodes.nodetype = 'ATTRIBUTE'"); |
|
979 | 1027 |
MetaCatUtil.debugMessage("Attribute query: " + self.toString(), 30); |
980 | 1028 |
|
981 | 1029 |
return self.toString(); |
src/edu/ucsb/nceas/metacat/DBQuery.java | ||
---|---|---|
31 | 31 |
|
32 | 32 |
package edu.ucsb.nceas.metacat; |
33 | 33 |
|
34 |
import edu.ucsb.nceas.morpho.datapackage.*; |
|
35 |
import java.io.*; |
|
34 |
import java.io.BufferedWriter; |
|
35 |
import java.io.File; |
|
36 |
import java.io.FileInputStream; |
|
37 |
import java.io.FileReader; |
|
38 |
import java.io.FileWriter; |
|
39 |
import java.io.IOException; |
|
40 |
import java.io.InputStream; |
|
41 |
import java.io.Reader; |
|
42 |
import java.io.StringReader; |
|
43 |
import java.io.StringWriter; |
|
44 |
import java.sql.PreparedStatement; |
|
45 |
import java.sql.ResultSet; |
|
46 |
import java.sql.SQLException; |
|
47 |
import java.util.Enumeration; |
|
48 |
import java.util.Hashtable; |
|
36 | 49 |
import java.util.StringTokenizer; |
37 | 50 |
import java.util.Vector; |
38 |
import java.util.zip.*; |
|
39 |
import java.net.URL; |
|
40 |
import java.net.MalformedURLException; |
|
41 |
import java.sql.*; |
|
42 |
import java.util.Stack; |
|
43 |
import java.util.Hashtable; |
|
44 |
import java.util.Enumeration; |
|
45 |
import java.io.File; |
|
46 |
import java.io.FileWriter; |
|
47 |
import java.io.BufferedWriter; |
|
51 |
import java.util.zip.ZipEntry; |
|
52 |
import java.util.zip.ZipOutputStream; |
|
53 |
|
|
48 | 54 |
import javax.servlet.ServletOutputStream; |
49 | 55 |
|
56 |
import edu.ucsb.nceas.morpho.datapackage.Triple; |
|
57 |
import edu.ucsb.nceas.morpho.datapackage.TripleCollection; |
|
58 |
|
|
50 | 59 |
/** |
51 | 60 |
* A Class that searches a relational DB for elements and |
52 | 61 |
* attributes that have free text matches a query string, |
... | ... | |
104 | 113 |
double connTime = System.currentTimeMillis(); |
105 | 114 |
|
106 | 115 |
// Execute the query |
107 |
DBQuery queryobj = new DBQuery(util.getOption("saxparser"));
|
|
116 |
DBQuery queryobj = new DBQuery(MetaCatUtil.getOption("saxparser"));
|
|
108 | 117 |
FileReader xml = new FileReader(new File(xmlfile)); |
109 | 118 |
Hashtable nodelist = null; |
110 | 119 |
nodelist = queryobj.findDocuments(xml, null, null, useXMLIndex); |
... | ... | |
211 | 220 |
// Get the XML query and covert it into a SQL statment |
212 | 221 |
QuerySpecification qspec = new QuerySpecification(xmlquery, |
213 | 222 |
parserName, |
214 |
util.getOption("accNumSeparator"));
|
|
223 |
MetaCatUtil.getOption("accNumSeparator"));
|
|
215 | 224 |
result = findDocuments(qspec, user, groups, useXMLIndex); |
216 | 225 |
} |
217 | 226 |
catch (IOException ioe) |
... | ... | |
310 | 319 |
&& !qspec.isPercentageSearch()) |
311 | 320 |
{ |
312 | 321 |
MetaCatUtil.debugMessage("Back tracing now...", 20); |
313 |
String sep = util.getOption("accNumSeparator");
|
|
322 |
String sep = MetaCatUtil.getOption("accNumSeparator");
|
|
314 | 323 |
StringBuffer btBuf = new StringBuffer(); |
315 | 324 |
btBuf.append("select docid from xml_relation where "); |
316 | 325 |
|
... | ... | |
342 | 351 |
{ //there was a backtrackable document found |
343 | 352 |
DocumentImpl xmldoc = null; |
344 | 353 |
String packageDocid = btrs.getString(1); |
345 |
util.debugMessage("Getting document for docid: "+packageDocid,40);
|
|
354 |
MetaCatUtil.debugMessage("Getting document for docid: "+packageDocid,40);
|
|
346 | 355 |
try |
347 | 356 |
{ |
348 | 357 |
// THIS CONSTRUCTOR BUILDS THE WHOLE XML doc not needed here |
... | ... | |
351 | 360 |
// xmldoc = new DocumentImpl(dbconn); |
352 | 361 |
xmldoc = new DocumentImpl(packageDocid, false); |
353 | 362 |
if (xmldoc == null) { |
354 |
util.debugMessage("Document was null for: "+packageDocid, 50);
|
|
363 |
MetaCatUtil.debugMessage("Document was null for: "+packageDocid, 50);
|
|
355 | 364 |
} |
356 | 365 |
} |
357 | 366 |
catch(Exception e) |
... | ... | |
362 | 371 |
|
363 | 372 |
String docid_org = xmldoc.getDocID(); |
364 | 373 |
if (docid_org == null) { |
365 |
util.debugMessage("Docid_org was null.", 40);
|
|
374 |
MetaCatUtil.debugMessage("Docid_org was null.", 40);
|
|
366 | 375 |
} |
367 | 376 |
docid = docid_org.trim(); |
368 | 377 |
docname = xmldoc.getDocname(); |
... | ... | |
373 | 382 |
|
374 | 383 |
document = new StringBuffer(); |
375 | 384 |
|
376 |
String completeDocid = docid + util.getOption("accNumSeparator");
|
|
385 |
String completeDocid = docid + MetaCatUtil.getOption("accNumSeparator");
|
|
377 | 386 |
completeDocid += rev; |
378 | 387 |
document.append("<docid>").append(completeDocid); |
379 | 388 |
document.append("</docid>"); |
... | ... | |
403 | 412 |
|
404 | 413 |
document = new StringBuffer(); |
405 | 414 |
|
406 |
String completeDocid = docid + util.getOption("accNumSeparator");
|
|
415 |
String completeDocid = docid + MetaCatUtil.getOption("accNumSeparator");
|
|
407 | 416 |
completeDocid += rev; |
408 | 417 |
document.append("<docid>").append(completeDocid).append("</docid>"); |
409 | 418 |
if (docname != null) { |
... | ... | |
472 | 481 |
MetaCatUtil.debugMessage("Time for execute access extended query: " |
473 | 482 |
+(extendedAccessQueryEnd-extendedQueryStart), 30); |
474 | 483 |
|
475 |
String extendedQuery = qspec.printExtendedSQL(doclist.toString(), |
|
476 |
controlPairs);
|
|
484 |
String extendedQuery = qspec.printExtendedSQL(doclist.toString(),
|
|
485 |
controlPairs, useXMLIndex);
|
|
477 | 486 |
MetaCatUtil.debugMessage("Extended query: "+ extendedQuery, 30); |
478 | 487 |
pstmt = dbconn.prepareStatement(extendedQuery); |
479 | 488 |
//increase dbconnection usage count |
... | ... | |
559 | 568 |
|
560 | 569 |
|
561 | 570 |
// get attribures return |
562 |
docListResult = getAttributeValueForReturn |
|
563 |
(qspec,docListResult, doclist.toString());
|
|
571 |
docListResult = getAttributeValueForReturn(qspec, docListResult,
|
|
572 |
doclist.toString(), useXMLIndex);
|
|
564 | 573 |
}//if doclist lenght is great than zero |
565 | 574 |
|
566 | 575 |
}//if has extended query |
... | ... | |
575 | 584 |
//String connstring = "metacat://"+util.getOption("server")+"?docid="; |
576 | 585 |
String connstring = "%docid="; |
577 | 586 |
String docidkey = (String)docidkeys.nextElement(); |
578 |
pstmt = dbconn.prepareStatement(qspec.printRelationSQL(docidkey));
|
|
587 |
pstmt = dbconn.prepareStatement(QuerySpecification.printRelationSQL(docidkey));
|
|
579 | 588 |
pstmt.execute(); |
580 | 589 |
rs = pstmt.getResultSet(); |
581 | 590 |
tableHasRows = rs.next(); |
... | ... | |
725 | 734 |
* A method to return search result after running a query which return |
726 | 735 |
* field have attribue |
727 | 736 |
*/ |
728 |
private Hashtable getAttributeValueForReturn(QuerySpecification squery, |
|
729 |
Hashtable docInformationList, |
|
730 |
String docList) |
|
737 |
private Hashtable getAttributeValueForReturn(QuerySpecification squery, |
|
738 |
Hashtable docInformationList, String docList, boolean useXMLIndex) |
|
731 | 739 |
{ |
732 | 740 |
StringBuffer XML = null; |
733 | 741 |
String sql = null; |
... | ... | |
746 | 754 |
// if has attribute as return field |
747 | 755 |
if (squery.containAttributeReturnField()) |
748 | 756 |
{ |
749 |
sql = squery.printAttributeQuery(docList); |
|
757 |
sql = squery.printAttributeQuery(docList, useXMLIndex);
|
|
750 | 758 |
try |
751 | 759 |
{ |
752 | 760 |
dbconn=DBConnectionPool.getDBConnection("DBQuery.getAttributeValue"); |
... | ... | |
1261 | 1269 |
}//try |
1262 | 1270 |
catch (SQLException e) |
1263 | 1271 |
{ |
1264 |
util.debugMessage("Error in isDataPackageId: "
|
|
1272 |
MetaCatUtil.debugMessage("Error in isDataPackageId: "
|
|
1265 | 1273 |
+e.getMessage(), 30); |
1266 | 1274 |
} |
1267 | 1275 |
finally |
... | ... | |
1425 | 1433 |
} |
1426 | 1434 |
|
1427 | 1435 |
String docidPlusVersion=((String)docIdList.elementAt(i)) |
1428 |
+util.getOption("accNumSeparator")+rev;
|
|
1436 |
+MetaCatUtil.getOption("accNumSeparator")+rev;
|
|
1429 | 1437 |
|
1430 | 1438 |
|
1431 | 1439 |
//create new documentImpl object |
... | ... | |
1517 | 1525 |
byte[] byteString = null; |
1518 | 1526 |
ZipEntry zEntry = null; |
1519 | 1527 |
// this is data file; add file to zip |
1520 |
String filePath = util.getOption("datafilepath");
|
|
1528 |
String filePath = MetaCatUtil.getOption("datafilepath");
|
|
1521 | 1529 |
if (!filePath.endsWith("/")) |
1522 | 1530 |
{ |
1523 | 1531 |
filePath += "/"; |
... | ... | |
1540 | 1548 |
}//try |
1541 | 1549 |
catch (IOException ioe) |
1542 | 1550 |
{ |
1543 |
util.debugMessage("There is an exception: "+ioe.getMessage(), 30);
|
|
1551 |
MetaCatUtil.debugMessage("There is an exception: "+ioe.getMessage(), 30);
|
|
1544 | 1552 |
}//catch |
1545 | 1553 |
}//addDataFileToZipOutputStream() |
1546 | 1554 |
|
... | ... | |
1673 | 1681 |
|
1674 | 1682 |
docImpls=new DocumentImpl(docId); |
1675 | 1683 |
//checking if the user has the permission to read the documents |
1676 |
if (docImpls.hasReadPermission(user,groups,docImpls.getDocID()))
|
|
1684 |
if (DocumentImpl.hasReadPermission(user,groups,docImpls.getDocID()))
|
|
1677 | 1685 |
{ |
1678 | 1686 |
zOut = new ZipOutputStream(out); |
1679 | 1687 |
//if the docImpls is metadata |
... | ... | |
1714 | 1722 |
version=currentVersion; |
1715 | 1723 |
//get package zip entry name |
1716 | 1724 |
//it should be docId.revsion.package |
1717 |
rootName=packageId+util.getOption("accNumSeparator")+version+
|
|
1718 |
util.getOption("accNumSeparator")+"package";
|
|
1725 |
rootName=packageId+MetaCatUtil.getOption("accNumSeparator")+version+
|
|
1726 |
MetaCatUtil.getOption("accNumSeparator")+"package";
|
|
1719 | 1727 |
//get the whole id list for data packadge |
1720 | 1728 |
docIdList=getCurrentDocidListForDataPackage(packageId); |
1721 | 1729 |
//get the whole documentImple object |
... | ... | |
1730 | 1738 |
else //for an old version |
1731 | 1739 |
{ |
1732 | 1740 |
|
1733 |
rootName=docIdString+util.getOption("accNumSeparator")+"package";
|
|
1741 |
rootName=docIdString+MetaCatUtil.getOption("accNumSeparator")+"package";
|
|
1734 | 1742 |
//get the whole id list for data packadge |
1735 | 1743 |
docIdList=getOldVersionDocidListForDataPackage(docIdString); |
1736 | 1744 |
|
... | ... | |
1793 | 1801 |
//create a docmentImpls object (represent xml doc) base on the docId |
1794 | 1802 |
docImpls=(DocumentImpl)documentImplList.elementAt(i); |
1795 | 1803 |
//checking if the user has the permission to read the documents |
1796 |
if (docImpls.hasReadPermission(user,groups,docImpls.getDocID()))
|
|
1804 |
if (DocumentImpl.hasReadPermission(user,groups,docImpls.getDocID()))
|
|
1797 | 1805 |
{ |
1798 | 1806 |
//if the docImpls is metadata |
1799 | 1807 |
if ((docImpls.getDoctype()).compareTo("BIN")!=0) |
... | ... | |
1859 | 1867 |
return xmlFieldValue; |
1860 | 1868 |
} |
1861 | 1869 |
|
1862 |
|
|
1863 | 1870 |
} |
1864 |
|
|
1865 | 1871 |
} |
Also available in: Unified diff
Changed printAttributeQuery() to no longer depend on the xml_index table. Now, if useXMLIndex is false, the method will use a recursive query on xml_nodes to match paths instead of using xml_index.