LUCENE-978: ensure all streams are closed when we hit exception in constructor

git-svn-id: https://svn.apache.org/repos/asf/lucene/java/trunk@567253 13f79535-47bb-0310-9956-ffa450edef68
This commit is contained in:
Michael McCandless 2007-08-18 09:42:21 +00:00
parent 06d4849ca8
commit c1a76d9dbe
4 changed files with 97 additions and 44 deletions

View File

@ -72,6 +72,10 @@ Bug fixes
sharing an index over NFS and using a custom deletion policy (Mike
McCandless)
11. LUCENE-978: Ensure TermInfosReader, FieldsReader, and FieldsReader
close any streams they had opened if an exception is hit in the
constructor. (Ning Li via Mike McCandless)
New features
1. LUCENE-906: Elision filter for French.

View File

@ -66,23 +66,38 @@ final class FieldsReader {
}
FieldsReader(Directory d, String segment, FieldInfos fn, int readBufferSize, int docStoreOffset, int size) throws IOException {
fieldInfos = fn;
boolean success = false;
cloneableFieldsStream = d.openInput(segment + ".fdt", readBufferSize);
fieldsStream = (IndexInput)cloneableFieldsStream.clone();
indexStream = d.openInput(segment + ".fdx", readBufferSize);
try {
fieldInfos = fn;
if (docStoreOffset != -1) {
// We read only a slice out of this shared fields file
this.docStoreOffset = docStoreOffset;
this.size = size;
cloneableFieldsStream = d.openInput(segment + ".fdt", readBufferSize);
fieldsStream = (IndexInput) cloneableFieldsStream.clone();
indexStream = d.openInput(segment + ".fdx", readBufferSize);
// Verify the file is long enough to hold all of our
// docs
assert ((int) (indexStream.length()/8)) >= size + this.docStoreOffset;
} else {
this.docStoreOffset = 0;
this.size = (int) (indexStream.length() >> 3);
if (docStoreOffset != -1) {
// We read only a slice out of this shared fields file
this.docStoreOffset = docStoreOffset;
this.size = size;
// Verify the file is long enough to hold all of our
// docs
assert ((int) (indexStream.length() / 8)) >= size + this.docStoreOffset;
} else {
this.docStoreOffset = 0;
this.size = (int) (indexStream.length() >> 3);
}
success = true;
} finally {
// With lock-less commits, it's entirely possible (and
// fine) to hit a FileNotFound exception above. In
// this case, we want to explicitly close any subset
// of things that were opened so that we don't have to
// wait for a GC to do so.
if (!success) {
close();
}
}
}
@ -103,9 +118,15 @@ final class FieldsReader {
*/
final void close() throws IOException {
if (!closed) {
fieldsStream.close();
cloneableFieldsStream.close();
indexStream.close();
if (fieldsStream != null) {
fieldsStream.close();
}
if (cloneableFieldsStream != null) {
cloneableFieldsStream.close();
}
if (indexStream != null) {
indexStream.close();
}
IndexInput localFieldsStream = (IndexInput) fieldsStreamTL.get();
if (localFieldsStream != null) {
localFieldsStream.close();

View File

@ -48,17 +48,31 @@ final class TermInfosReader {
TermInfosReader(Directory dir, String seg, FieldInfos fis, int readBufferSize)
throws CorruptIndexException, IOException {
directory = dir;
segment = seg;
fieldInfos = fis;
boolean success = false;
origEnum = new SegmentTermEnum(directory.openInput(segment + ".tis", readBufferSize),
fieldInfos, false);
size = origEnum.size;
try {
directory = dir;
segment = seg;
fieldInfos = fis;
indexEnum =
new SegmentTermEnum(directory.openInput(segment + ".tii", readBufferSize),
fieldInfos, true);
origEnum = new SegmentTermEnum(directory.openInput(segment + ".tis",
readBufferSize), fieldInfos, false);
size = origEnum.size;
indexEnum = new SegmentTermEnum(directory.openInput(segment + ".tii",
readBufferSize), fieldInfos, true);
success = true;
} finally {
// With lock-less commits, it's entirely possible (and
// fine) to hit a FileNotFound exception above. In
// this case, we want to explicitly close any subset
// of things that were opened so that we don't have to
// wait for a GC to do so.
if (!success) {
close();
}
}
}
public int getSkipInterval() {

View File

@ -53,26 +53,40 @@ class TermVectorsReader implements Cloneable {
TermVectorsReader(Directory d, String segment, FieldInfos fieldInfos, int readBufferSize, int docStoreOffset, int size)
throws CorruptIndexException, IOException {
if (d.fileExists(segment + TermVectorsWriter.TVX_EXTENSION)) {
tvx = d.openInput(segment + TermVectorsWriter.TVX_EXTENSION, readBufferSize);
checkValidFormat(tvx);
tvd = d.openInput(segment + TermVectorsWriter.TVD_EXTENSION, readBufferSize);
tvdFormat = checkValidFormat(tvd);
tvf = d.openInput(segment + TermVectorsWriter.TVF_EXTENSION, readBufferSize);
tvfFormat = checkValidFormat(tvf);
if (-1 == docStoreOffset) {
this.docStoreOffset = 0;
this.size = (int) (tvx.length() >> 3);
} else {
this.docStoreOffset = docStoreOffset;
this.size = size;
// Verify the file is long enough to hold all of our
// docs
assert ((int) (tvx.length()/8)) >= size + docStoreOffset;
boolean success = false;
try {
if (d.fileExists(segment + TermVectorsWriter.TVX_EXTENSION)) {
tvx = d.openInput(segment + TermVectorsWriter.TVX_EXTENSION, readBufferSize);
checkValidFormat(tvx);
tvd = d.openInput(segment + TermVectorsWriter.TVD_EXTENSION, readBufferSize);
tvdFormat = checkValidFormat(tvd);
tvf = d.openInput(segment + TermVectorsWriter.TVF_EXTENSION, readBufferSize);
tvfFormat = checkValidFormat(tvf);
if (-1 == docStoreOffset) {
this.docStoreOffset = 0;
this.size = (int) (tvx.length() >> 3);
} else {
this.docStoreOffset = docStoreOffset;
this.size = size;
// Verify the file is long enough to hold all of our
// docs
assert ((int) (tvx.length() / 8)) >= size + docStoreOffset;
}
}
this.fieldInfos = fieldInfos;
success = true;
} finally {
// With lock-less commits, it's entirely possible (and
// fine) to hit a FileNotFound exception above. In
// this case, we want to explicitly close any subset
// of things that were opened so that we don't have to
// wait for a GC to do so.
if (!success) {
close();
}
}
this.fieldInfos = fieldInfos;
}
private int checkValidFormat(IndexInput in) throws CorruptIndexException, IOException