use of com.spotify.docker.client.LogMessage in project helios by spotify.
the class LoggingLogStreamFollower method followLog.
@Override
public void followLog(final JobId jobId, final String containerId, final Iterator<LogMessage> logStream) throws IOException {
final Map<LogMessage.Stream, Decoder> streamDecoders = createStreamDecoders();
final StringBuilder stringBuilder = new StringBuilder();
LogMessage.Stream lastStream = null;
try {
while (logStream.hasNext()) {
final LogMessage message = logStream.next();
final ByteBuffer content = message.content();
final LogMessage.Stream stream = message.stream();
if (lastStream != null && lastStream != stream && stringBuilder.length() > 0) {
log(lastStream, containerId, jobId, stringBuilder);
}
final Decoder decoder = streamDecoders.get(stream);
final CharsetDecoder charsetDecoder = decoder.charsetDecoder;
final ByteBuffer byteBuffer = decoder.byteBuffer;
final CharBuffer charBuffer = decoder.charBuffer;
while (content.hasRemaining()) {
// Transfer as much of content into byteBuffer that we have room for
byteBuffer.put(content);
byteBuffer.flip();
// Decode as much of byteBuffer into charBuffer that we can
charsetDecoder.decode(byteBuffer, charBuffer, false);
// The decoder might have left some partial byte sequences in the byteBuffer... Since we
// don't have a ring buffer we should compact the buffer to not overflow.
// We MUST NOT clear the byteBuffer since then we can lose those partial byte sequences.
byteBuffer.compact();
// Now start consuming the charBuffer
charBuffer.flip();
// Heuristic to avoid allocations... this will allocate too much memory if the charBuffer
// contains any newlines or other special chars
stringBuilder.ensureCapacity(charBuffer.remaining());
while (charBuffer.hasRemaining()) {
final char c = charBuffer.get();
switch(c) {
case '\n':
log(stream, containerId, jobId, stringBuilder);
break;
default:
stringBuilder.append(c);
}
}
// This buffer is completely drained so we can reset it
charBuffer.clear();
}
lastStream = stream;
}
} finally {
if (lastStream != null && stringBuilder.length() > 0) {
// Yes, we are not checking for any trailing bytes in the decoder byteBuffers here. That
// means that if the container wrote partial UTF-8 sequences before EOF they will be
// discarded.
log(lastStream, containerId, jobId, stringBuilder);
}
}
}
use of com.spotify.docker.client.LogMessage in project helios by spotify.
the class InMemoryLogStreamFollower method followLog.
@Override
public void followLog(final JobId jobId, final String containerId, final Iterator<LogMessage> logStream) throws IOException {
try (final ByteArrayOutputStream stdout = new ByteArrayOutputStream();
final ByteArrayOutputStream stderr = new ByteArrayOutputStream()) {
streamHolders.put(jobId, new StreamHolder(stdout, stderr));
while (logStream.hasNext()) {
final LogMessage message = logStream.next();
final ByteBuffer content = message.content();
switch(message.stream()) {
case STDOUT:
writeAndFlush(content, stdout);
break;
case STDERR:
writeAndFlush(content, stderr);
break;
case STDIN:
default:
break;
}
}
}
}
Aggregations