package org.glassfish.grizzly.filterchain;
import java.io.IOException;
import org.glassfish.grizzly.Connection;
import org.glassfish.grizzly.TransformationException;
import org.glassfish.grizzly.TransformationResult;
import org.glassfish.grizzly.Transformer;
public abstract class AbstractCodecFilter<K, L> extends BaseFilter implements CodecFilter<K, L> {
private final Transformer<K, L> decoder;
private final Transformer<L, K> encoder;
public AbstractCodecFilter(final Transformer<K, L> decoder, final Transformer<L, K> encoder) {
this.decoder = decoder;
this.encoder = encoder;
}
@Override
@SuppressWarnings("unchecked")
public NextAction handleRead(final FilterChainContext ctx) throws IOException {
final Connection connection = ctx.getConnection();
final K message = ctx.getMessage();
final TransformationResult<K, L> result = decoder.transform(connection, message);
switch (result.getStatus()) {
case COMPLETE:
final K remainder = result.getExternalRemainder();
final boolean hasRemaining = decoder.hasInputRemaining(connection, remainder);
decoder.release(connection);
ctx.setMessage(result.getMessage());
return hasRemaining ? ctx.getInvokeAction(remainder) : ctx.getInvokeAction();
case INCOMPLETE:
return ctx.getStopAction(message);
case ERROR:
throw new TransformationException(getClass().getName() + " transformation error: (" + result.getErrorCode() + ") " + result.getErrorDescription());
}
return ctx.getInvokeAction();
}
@Override
@SuppressWarnings("unchecked")
public NextAction handleWrite(final FilterChainContext ctx) throws IOException {
final Connection connection = ctx.getConnection();
final L message = ctx.getMessage();
final TransformationResult<L, K> result = encoder.transform(connection, message);
switch (result.getStatus()) {
case COMPLETE:
ctx.setMessage(result.getMessage());
final L remainder = result.getExternalRemainder();
final boolean hasRemaining = encoder.hasInputRemaining(connection, remainder);
encoder.release(connection);
return hasRemaining ? ctx.getInvokeAction(remainder) : ctx.getInvokeAction();
case INCOMPLETE:
return ctx.getStopAction(message);
case ERROR:
throw new TransformationException(getClass().getName() + " transformation error: (" + result.getErrorCode() + ") " + result.getErrorDescription());
}
return ctx.getInvokeAction();
}
@Override
public Transformer<K, L> getDecoder() {
return decoder;
}
@Override
public Transformer<L, K> getEncoder() {
return encoder;
}
}