BATCH-2052: StaxEventItemWriter should only force sync once per chunk

This commit is contained in:
jpraet
2013-06-29 13:54:24 +02:00
committed by Michael Minella
parent 0c892da257
commit 36e3bda486
4 changed files with 129 additions and 62 deletions

View File

@@ -614,6 +614,7 @@ InitializingBean {
});
writer.setEncoding(encoding);
writer.setForceSync(forceSync);
return writer;
}
else {
@@ -627,7 +628,7 @@ InitializingBean {
}
};
return new BufferedWriter(writer);
return writer;
}
}
catch (UnsupportedCharsetException ucse) {

View File

@@ -395,7 +395,6 @@ ResourceAwareItemWriterItemStream<T>, InitializingBean {
/**
* Helper method for opening output source at given file position
*/
@SuppressWarnings("resource")
private void open(long position, boolean restarted) {
File file;
@@ -443,25 +442,20 @@ ResourceAwareItemWriterItemStream<T>, InitializingBean {
});
writer.setEncoding(encoding);
writer.setForceSync(forceSync);
bufferedWriter = writer;
}
else {
Writer writer = new BufferedWriter(new OutputStreamWriter(os, encoding)) {
@Override
public void flush() throws IOException {
super.flush();
if (forceSync) {
channel.force(false);
}
}
};
bufferedWriter = writer;
bufferedWriter = new BufferedWriter(new OutputStreamWriter(os, encoding));
}
delegateEventWriter = createXmlEventWriter(outputFactory, bufferedWriter);
eventWriter = new NoStartEndDocumentStreamWriter(delegateEventWriter);
initNamespaceContext(delegateEventWriter);
if (!restarted) {
startDocument(delegateEventWriter);
if (forceSync) {
channel.force(false);
}
}
}
catch (XMLStreamException xse) {
@@ -470,8 +464,10 @@ ResourceAwareItemWriterItemStream<T>, InitializingBean {
catch (UnsupportedEncodingException e) {
throw new DataAccessResourceFailureException("Unable to write to file resource: [" + resource
+ "] with encoding=[" + encoding + "]", e);
}
catch (IOException e) {
throw new DataAccessResourceFailureException("Unable to write to file resource: [" + resource + "]", e);
}
}
/**
@@ -716,9 +712,15 @@ ResourceAwareItemWriterItemStream<T>, InitializingBean {
}
try {
eventWriter.flush();
if (forceSync) {
channel.force(false);
}
}
catch (XMLStreamException e) {
throw new WriteFailedException("Failed to flush the events", e);
}
catch (IOException e) {
throw new WriteFailedException("Failed to flush the events", e);
}
}

View File

@@ -48,12 +48,14 @@ public class TransactionAwareBufferedWriter extends Writer {
private FileChannel channel;
private final Runnable closeCallback;
// default encoding for writing to output files - set to UTF-8.
private static final String DEFAULT_CHARSET = "UTF-8";
private String encoding = DEFAULT_CHARSET;
private boolean forceSync = false;
/**
* Create a new instance with the underlying file channel provided, and a callback
* to execute on close. The callback should clean up related resources like
@@ -74,6 +76,19 @@ public class TransactionAwareBufferedWriter extends Writer {
this.encoding = encoding;
}
/**
* Flag to indicate that changes should be force-synced to disk on flush.
* Defaults to false, which means that even with a local disk changes could
* be lost if the OS crashes in between a write and a cache flush. Setting
* to true may result in slower performance for usage patterns involving
* many frequent writes.
*
* @param forceSync the flag value to set
*/
public void setForceSync(boolean forceSync) {
this.forceSync = forceSync;
}
/**
* @return
*/
@@ -88,7 +103,7 @@ public class TransactionAwareBufferedWriter extends Writer {
public void afterCompletion(int status) {
clear();
}
@Override
public void beforeCommit(boolean readOnly) {
try {
@@ -112,6 +127,9 @@ public class TransactionAwareBufferedWriter extends Writer {
if(bytesWritten != bufferLength) {
throw new IOException("All bytes to be written were not successfully written");
}
if (forceSync) {
channel.force(false);
}
if (TransactionSynchronizationManager.hasResource(closeKey)) {
closeCallback.run();
}
@@ -145,7 +163,7 @@ public class TransactionAwareBufferedWriter extends Writer {
if (!transactionActive()) {
return 0L;
}
try {
try {
return getCurrentBuffer().toString().getBytes(encoding).length;
} catch (UnsupportedEncodingException e) {
throw new WriteFailedException("Could not determine buffer size because of unsupported encoding: " + encoding, e);
@@ -182,7 +200,7 @@ public class TransactionAwareBufferedWriter extends Writer {
*/
@Override
public void flush() throws IOException {
if (!transactionActive()) {
if (!transactionActive() && forceSync) {
channel.force(false);
}
}