package com.zendesk.maxwell.row;
import com.zendesk.maxwell.util.ListWithDiskBuffer;
import java.io.IOException;
public class RowMapBuffer extends ListWithDiskBuffer<RowMap> {
private static long FlushOutputStreamBytes = 10000000;
private Long xid;
private Long serverId;
private Long threadId;
private long memorySize = 0;
private long outputStreamCacheSize = 0;
private final long maxMemory;
public RowMapBuffer(long maxInMemoryElements) {
super(maxInMemoryElements);
this.maxMemory = (long) (Runtime.getRuntime().maxMemory() * 0.25);
}
public RowMapBuffer(long maxInMemoryElements, long maxMemory) {
super(maxInMemoryElements);
this.maxMemory = maxMemory;
}
@Override
public void add(RowMap rowMap) throws IOException {
this.memorySize += rowMap.getApproximateSize();
super.add(rowMap);
}
@Override
protected boolean shouldBuffer() {
return memorySize > maxMemory;
}
@Override
protected RowMap evict() throws IOException {
RowMap r = super.evict();
this.memorySize -= r.getApproximateSize();
/* For performance reasons, the output stream will hold on to cached objects.
* There's probably a smarter thing to do (write our own serdes, maybe?), but
* for now we forcibly flush its cache when it gets too big. */
this.outputStreamCacheSize += r.getApproximateSize();
if ( this.outputStreamCacheSize > FlushOutputStreamBytes ) {
resetOutputStreamCaches();
this.outputStreamCacheSize = 0;
}
return r;
}
public RowMap removeFirst() throws IOException, ClassNotFoundException {
RowMap r = super.removeFirst(RowMap.class);
r.setXid(this.xid);
r.setServerId(this.serverId);
r.setThreadId(this.threadId);
return r;
}
public void setXid(Long xid) {
this.xid = xid;
}
public void setServerId(Long serverId) {
this.serverId = serverId;
}
public void setThreadId(Long threadId) {
this.threadId = threadId;
}
}