package org.ch3ck3r.jgbx;
import java.io.IOException;
import java.io.OutputStream;
import java.nio.charset.Charset;
import java.util.concurrent.ArrayBlockingQueue;
import java.util.concurrent.TimeUnit;
import org.apache.log4j.Logger;
import org.ch3ck3r.jgbx.internal.RequestContainer;
import org.ch3ck3r.jgbx.utils.ByteOrderUtils;
/**
* The JGBX request sender thread
*
* @author Frank Zechert
* @version 1
*/
class SenderThread extends Thread {
/**
* The logger.
*/
private final static Logger logger = Logger.getLogger(SenderThread.class);
/**
* The polling timeout in milliseconds.
*/
private static final int POLLING_TIMEOUT = 100;
/**
* Indicates that this thread should exit.
*/
private boolean shouldExit;
/**
* The JGBXConnector instance.
*/
private final JGBXConnector jgbxc;
/**
* The output stream to send something to.
*/
private final OutputStream outputStream;
/**
* The request queue to work on.
*/
private final ArrayBlockingQueue<RequestContainer> requestQueue;
/**
* Create a new sender thread.
*
* @param jgbxConnector
* the JGBXConnector
* @param outputStream
* The output stream.
* @param requestQueue
* The request queue to work on.
*/
public SenderThread(final JGBXConnector jgbxConnector, final OutputStream outputStream,
final ArrayBlockingQueue<RequestContainer> requestQueue) {
super("JGBX Request Sender Thread");
this.shouldExit = false;
this.jgbxc = jgbxConnector;
this.outputStream = outputStream;
this.requestQueue = requestQueue;
}
/**
* Exit this thread.
*/
public void exit() {
logger.debug("SenderThread was asked to exit.");
this.shouldExit = true;
}
/**
* Start polling the request queue and send the requests to the server.
*/
@Override
public void run() {
logger.info("SenderThread is running");
while (!this.shouldExit && this.jgbxc.isConnected()) {
try {
final RequestContainer requestC = this.requestQueue.poll(POLLING_TIMEOUT, TimeUnit.MILLISECONDS);
if (requestC == null) {
continue;
}
final String message = requestC.getRequest().toXML();
logger.debug("Sending request: [" + message.length() + "] [" + requestC.getHandle() + "] " + message);
final byte[] messageBytes = message.getBytes(Charset.forName("UTF-8"));
final Integer messageLength = messageBytes.length;
final byte[] messageLengthBytes = ByteOrderUtils.integerToLittleEndianess(messageLength);
final byte[] messageHandleBytes = ByteOrderUtils.integerToLittleEndianess(requestC.getHandle());
try {
this.outputStream.write(messageLengthBytes);
this.outputStream.write(messageHandleBytes);
this.outputStream.write(messageBytes);
this.outputStream.flush();
}
catch (final IOException e) {
logger.error(e);
this.jgbxc.disconnect();
}
}
catch (final Throwable e) {
logger.error(e);
this.jgbxc.disconnect();
break;
}
}
logger.info("SenderThread exited");
}
}