Revision 7824
Added by ben leinfelder over 11 years ago
src/edu/ucsb/nceas/metacat/DocumentImpl.java | ||
---|---|---|
31 | 31 |
import java.io.ByteArrayInputStream; |
32 | 32 |
import java.io.ByteArrayOutputStream; |
33 | 33 |
import java.io.File; |
34 |
import java.io.FileInputStream; |
|
34 | 35 |
import java.io.FileOutputStream; |
35 | 36 |
import java.io.IOException; |
36 | 37 |
import java.io.InputStream; |
... | ... | |
1058 | 1059 |
* matter withinInlineData's value, the document will |
1059 | 1060 |
* |
1060 | 1061 |
*/ |
1061 |
public void toXml(OutputStream out, String user, String[] groups, boolean withInLineData)
|
|
1062 |
public InputStream toXml(OutputStream out, String user, String[] groups, boolean withInLineData)
|
|
1062 | 1063 |
throws McdbException { |
1063 | 1064 |
String documentDir = null; |
1064 | 1065 |
String documentPath = null; |
... | ... | |
1084 | 1085 |
throw new McdbException("Attempting to read a zero length document from disk: " + documentPath); |
1085 | 1086 |
} |
1086 | 1087 |
|
1087 |
readFromFileSystem(out, user, groups, documentPath); |
|
1088 |
return readFromFileSystem(out, user, groups, documentPath);
|
|
1088 | 1089 |
} |
1089 | 1090 |
|
1090 | 1091 |
/** |
... | ... | |
1406 | 1407 |
* the location of the document on disk |
1407 | 1408 |
* |
1408 | 1409 |
*/ |
1409 |
public void readFromFileSystem(
|
|
1410 |
public InputStream readFromFileSystem(
|
|
1410 | 1411 |
OutputStream out, String user, String[] groups, String documentPath) throws McdbException { |
1411 | 1412 |
|
1412 |
String xmlFileContents = ""; |
|
1413 |
String xmlFileContents = null; |
|
1414 |
String encoding = null; |
|
1413 | 1415 |
|
1414 | 1416 |
try { |
1415 |
// detect and use correct encoding |
|
1416 |
xmlFileContents = FileUtil.readFileToString(documentPath); |
|
1417 |
// guess the encoding from default bytes |
|
1418 |
XmlStreamReader xsr = new XmlStreamReader(new ByteArrayInputStream(xmlFileContents.getBytes())); |
|
1419 |
String encoding = xsr.getEncoding(); |
|
1420 |
// reread the contents using the correct encoding |
|
1421 |
if (encoding != null) { |
|
1422 |
xmlFileContents = FileUtil.readFileToString(documentPath, encoding); |
|
1423 |
} |
|
1424 | 1417 |
|
1425 | 1418 |
// get a list of inline data sections that are not readable |
1426 | 1419 |
// by this user |
... | ... | |
1431 | 1424 |
// If this is for each unreadable section, strip the inline data |
1432 | 1425 |
// from the doc |
1433 | 1426 |
if (unReadableInlineDataList.size() > 0 && doctype != null) { |
1427 |
|
|
1428 |
// detect and use correct encoding |
|
1429 |
xmlFileContents = FileUtil.readFileToString(documentPath); |
|
1430 |
// guess the encoding from default bytes |
|
1431 |
XmlStreamReader xsr = new XmlStreamReader(new ByteArrayInputStream(xmlFileContents.getBytes())); |
|
1432 |
encoding = xsr.getEncoding(); |
|
1433 |
xsr.close(); |
|
1434 |
// reread the contents using the correct encoding |
|
1435 |
if (encoding != null) { |
|
1436 |
xmlFileContents = FileUtil.readFileToString(documentPath, encoding); |
|
1437 |
} |
|
1438 |
|
|
1434 | 1439 |
Set<String> inlineKeySet = unReadableInlineDataList.keySet(); |
1435 |
|
|
1436 | 1440 |
boolean pre210Doc = doctype.equals(EML2_0_0NAMESPACE) |
1437 | 1441 |
|| doctype.equals(EML2_0_1NAMESPACE); |
1438 | 1442 |
|
... | ... | |
1443 | 1447 |
// on whether this is a 2.0.1 or earlier doc or 2.1.0 and later. This |
1444 | 1448 |
// is because of eml schema changes for inline access. |
1445 | 1449 |
if (pre210Doc) { |
1446 |
xmlFileContents = stripInline20XData(xmlFileContents, |
|
1447 |
inlineKey); |
|
1450 |
xmlFileContents = stripInline20XData(xmlFileContents, inlineKey); |
|
1448 | 1451 |
} else { |
1449 | 1452 |
xmlFileContents = stripInline21XData(xmlFileContents, inlineKey); |
1450 | 1453 |
} |
... | ... | |
1452 | 1455 |
} |
1453 | 1456 |
} |
1454 | 1457 |
|
1455 |
// write with the detected encoding |
|
1456 |
Writer pw = new OutputStreamWriter(out, encoding); |
|
1457 |
// write the doc |
|
1458 |
pw.write(xmlFileContents); |
|
1459 |
pw.close(); |
|
1458 |
// will get input either from string content or file on disk |
|
1459 |
InputStream is = null; |
|
1460 | 1460 |
|
1461 |
// get the input stream |
|
1462 |
if (xmlFileContents != null) { |
|
1463 |
is = IOUtils.toInputStream(xmlFileContents, encoding); |
|
1464 |
} else { |
|
1465 |
is = new FileInputStream(documentPath); |
|
1466 |
} |
|
1467 |
|
|
1468 |
// send it to out |
|
1469 |
if (out != null) { |
|
1470 |
IOUtils.copyLarge(is, out); |
|
1471 |
} |
|
1472 |
// return the stream |
|
1473 |
return is; |
|
1474 |
|
|
1461 | 1475 |
} catch (UtilException e) { |
1462 | 1476 |
throw new McdbException(e.getMessage()); |
1463 | 1477 |
} catch (IOException e) { |
1464 | 1478 |
throw new McdbException(e.getMessage()); |
1465 | 1479 |
} |
1480 |
|
|
1466 | 1481 |
} |
1467 | 1482 |
|
1468 | 1483 |
/** |
src/edu/ucsb/nceas/metacat/MetacatHandler.java | ||
---|---|---|
30 | 30 |
import java.io.File; |
31 | 31 |
import java.io.FileInputStream; |
32 | 32 |
import java.io.FileNotFoundException; |
33 |
import java.io.FileOutputStream; |
|
34 | 33 |
import java.io.IOException; |
35 | 34 |
import java.io.InputStream; |
36 | 35 |
import java.io.InputStreamReader; |
... | ... | |
49 | 48 |
import java.sql.Timestamp; |
50 | 49 |
import java.text.ParseException; |
51 | 50 |
import java.text.SimpleDateFormat; |
52 |
import java.util.Date; |
|
53 | 51 |
import java.util.Enumeration; |
54 | 52 |
import java.util.HashMap; |
55 | 53 |
import java.util.Hashtable; |
... | ... | |
1009 | 1007 |
* @throws ClassNotFoundException |
1010 | 1008 |
* @throws IOException |
1011 | 1009 |
*/ |
1012 |
public static InputStream read(String docid) |
|
1013 |
throws ParseLSIDException, |
|
1014 |
PropertyNotFoundException, McdbException, SQLException, |
|
1015 |
ClassNotFoundException, IOException |
|
1016 |
{ |
|
1017 |
logMetacat.debug("MetacatHandler.read() called."); |
|
1018 |
|
|
1019 |
InputStream fileInputStream = null; |
|
1020 |
File tmpDir = null; |
|
1021 |
|
|
1022 |
// be sure we have a local ID from an LSID |
|
1023 |
if (docid.startsWith("urn:")) { |
|
1024 |
try { |
|
1025 |
docid = LSIDUtil.getDocId(docid, true); |
|
1026 |
|
|
1027 |
} catch ( ParseLSIDException ple ) { |
|
1028 |
logMetacat.debug("There was a problem parsing the LSID. The " + |
|
1029 |
"error message was: " + ple.getMessage()); |
|
1030 |
throw ple; |
|
1031 |
} |
|
1032 |
} |
|
1033 |
|
|
1034 |
// accomodate old clients that send docids without revision numbers |
|
1035 |
docid = DocumentUtil.appendRev(docid); |
|
1036 |
|
|
1037 |
DocumentImpl doc = new DocumentImpl(docid, false); |
|
1038 |
|
|
1039 |
// deal with data or metadata cases |
|
1040 |
if (doc.getRootNodeID() == 0) { |
|
1041 |
|
|
1042 |
// this is a data file |
|
1043 |
|
|
1044 |
// get the path to the file to read |
|
1045 |
try { |
|
1046 |
String filepath = PropertyService.getProperty("application.datafilepath"); |
|
1047 |
|
|
1048 |
// ensure it is a directory path |
|
1049 |
if ( !(filepath.endsWith("/")) ) { |
|
1050 |
filepath += "/"; |
|
1051 |
|
|
1052 |
} |
|
1053 |
String filename = filepath + docid; |
|
1054 |
fileInputStream = (InputStream) readFromFilesystem(filename); |
|
1055 |
|
|
1056 |
} catch ( PropertyNotFoundException pnf ) { |
|
1057 |
logMetacat.debug("There was a problem finding the " + |
|
1058 |
"application.datafilepath property. The error " + |
|
1059 |
"message was: " + pnf.getMessage()); |
|
1060 |
throw pnf; |
|
1061 |
|
|
1062 |
} // end try() |
|
1010 |
public static InputStream read(String docid) throws ParseLSIDException, |
|
1011 |
PropertyNotFoundException, McdbException, SQLException, |
|
1012 |
ClassNotFoundException, IOException { |
|
1013 |
logMetacat.debug("MetacatHandler.read() called."); |
|
1063 | 1014 |
|
1064 |
} else { |
|
1065 |
|
|
1066 |
// this is an metadata document |
|
1067 |
|
|
1068 |
// get a temporary file handle to write to as an OutputStream |
|
1069 |
try { |
|
1070 |
tmpDir = new File(PropertyService.getProperty("application.tempDir")); |
|
1015 |
InputStream inputStream = null; |
|
1071 | 1016 |
|
1072 |
} catch ( PropertyNotFoundException pnfe ) { |
|
1073 |
logMetacat.debug("There was a problem getting the" + |
|
1074 |
"application.tempDir property. Using /tmp " + |
|
1075 |
"instead. The error was: " + pnfe.getMessage()); |
|
1076 |
tmpDir = new File("/tmp"); |
|
1017 |
// be sure we have a local ID from an LSID |
|
1018 |
if (docid.startsWith("urn:")) { |
|
1019 |
try { |
|
1020 |
docid = LSIDUtil.getDocId(docid, true); |
|
1021 |
} catch (ParseLSIDException ple) { |
|
1022 |
logMetacat.debug("There was a problem parsing the LSID. The " |
|
1023 |
+ "error message was: " + ple.getMessage()); |
|
1024 |
throw ple; |
|
1025 |
} |
|
1026 |
} |
|
1077 | 1027 |
|
1078 |
} //end try() |
|
1079 |
|
|
1080 |
final File outputFile = File.createTempFile("metacat.output", null, tmpDir); |
|
1081 |
OutputStream out = new FileOutputStream(outputFile); |
|
1028 |
// accomodate old clients that send docids without revision numbers |
|
1029 |
docid = DocumentUtil.appendRev(docid); |
|
1030 |
DocumentImpl doc = new DocumentImpl(docid, false); |
|
1082 | 1031 |
|
1083 |
// Try to get the metadata file from disk. If it isn't |
|
1084 |
// found, create it from the db and write it to disk then. |
|
1085 |
try { |
|
1086 |
doc.toXml(out, null, null, true); |
|
1087 |
|
|
1088 |
} catch (McdbException e) { |
|
1089 |
// any exceptions in reading the xml from disc, and we go back to the |
|
1090 |
// old way of creating the xml directly. |
|
1091 |
logMetacat.error("MetacatHandler.readFromMetacat() " + |
|
1092 |
"- could not read from document file " + |
|
1093 |
docid + ": " + e.getMessage()); |
|
1094 |
e.printStackTrace(System.out); |
|
1095 |
doc.toXmlFromDb(out, null, null, true); |
|
1096 |
} |
|
1097 |
|
|
1098 |
// set the input stream |
|
1099 |
fileInputStream = new FileInputStream(outputFile); |
|
1100 |
outputFile.deleteOnExit(); |
|
1101 |
|
|
1102 |
} |
|
1103 |
|
|
1104 |
return fileInputStream; |
|
1105 |
} |
|
1032 |
// deal with data or metadata cases |
|
1033 |
if (doc.getRootNodeID() == 0) { |
|
1034 |
|
|
1035 |
// this is a data file |
|
1036 |
// get the path to the file to read |
|
1037 |
try { |
|
1038 |
String filepath = PropertyService.getProperty("application.datafilepath"); |
|
1039 |
// ensure it is a directory path |
|
1040 |
if (!(filepath.endsWith("/"))) { |
|
1041 |
filepath += "/"; |
|
1042 |
} |
|
1043 |
String filename = filepath + docid; |
|
1044 |
inputStream = readFromFilesystem(filename); |
|
1045 |
} catch (PropertyNotFoundException pnf) { |
|
1046 |
logMetacat.debug("There was a problem finding the " |
|
1047 |
+ "application.datafilepath property. The error " |
|
1048 |
+ "message was: " + pnf.getMessage()); |
|
1049 |
throw pnf; |
|
1050 |
} // end try() |
|
1051 |
|
|
1052 |
} else { |
|
1053 |
// this is an metadata document |
|
1054 |
// Get the xml (will try disk then DB) |
|
1055 |
try { |
|
1056 |
// force the InputStream to be returned |
|
1057 |
OutputStream nout = null; |
|
1058 |
inputStream = doc.toXml(nout, null, null, true); |
|
1059 |
} catch (McdbException e) { |
|
1060 |
// report the error |
|
1061 |
logMetacat.error( |
|
1062 |
"MetacatHandler.readFromMetacat() " |
|
1063 |
+ "- could not read document " + docid + ": " |
|
1064 |
+ e.getMessage(), e); |
|
1065 |
} |
|
1066 |
|
|
1067 |
} |
|
1068 |
|
|
1069 |
return inputStream; |
|
1070 |
} |
|
1106 | 1071 |
|
1107 | 1072 |
/** |
1108 | 1073 |
* Read a file from Metacat's configured file system data directory. |
Also available in: Unified diff
do not use tmp file to return an inputstream on read() operations - just read from the file we already have. https://projects.ecoinformatics.org/ecoinfo/issues/6009