use of com.sun.messaging.jmq.jmsserver.multibroker.raptor.ClusterTransferFileEndInfo in project openmq by eclipse-ee4j.
the class ClusterImpl method transferFiles.
@Override
public void transferFiles(String[] fileNames, BrokerAddress targetBroker, Long syncTimeout, String uuid, String myBrokerID, String module, FileTransferCallback callback) throws BrokerException {
String to = targetBroker.toString();
Socket socket = null;
MessageDigest digest = null;
try {
if (fileTransferShutdownOut) {
String emsg = br.getKString(br.W_CLUSTER_SERVICE_SHUTDOWN);
logger.log(logger.WARNING, emsg);
throw new BrokerException(emsg);
}
try {
digest = MessageDigest.getInstance("SHA1");
} catch (Exception e) {
String emsg = "";
if (e instanceof NoSuchAlgorithmException) {
emsg = "Unable to create MessageDigest for file transfer";
logger.log(logger.ERROR, emsg + ": " + e);
} else {
emsg = "Unexpectd exception in creating MessageDigest for file transfer";
logger.logStack(logger.ERROR, emsg, e);
}
throw new BrokerException(emsg, e);
}
logger.log(logger.INFO, br.getKString(br.I_CONNECT_REMOTE_FOR_FILE_TX, targetBroker));
socket = BrokerLink.makeSocket((BrokerAddressImpl) targetBroker, this, false, null);
to += "[" + socket.getInetAddress() + "]";
try {
socket.setTcpNoDelay(false);
} catch (Exception e) {
logger.log(logger.WARNING, "Failed to set socket TCP_NODELAY for file transfer: " + e);
}
try {
socket.setSoTimeout((int) Math.min(FILE_TRANSFER_SOTIMEOUT_OUT, syncTimeout.longValue()));
} catch (Exception e) {
logger.log(logger.WARNING, "Failed to set socket timeout for file transfer: " + e);
}
OutputStream os = socket.getOutputStream();
logger.log(logger.INFO, br.getKString(br.I_CLUSTER_SEND_TX_FILE_LINK_REQUEST, to));
Packet pkt = getLinkInitPkt(Integer.valueOf(LinkInfo.SERVICE_FILE_TRANSFER));
pkt.writePacket(os);
os.flush();
int numFiles = fileNames.length;
ClusterTransferFileListInfo tfl = ClusterTransferFileListInfo.newInstance(uuid, myBrokerID, Integer.valueOf(numFiles), FileTransferCallback.STORE);
Object[] tmpargs = { String.valueOf(numFiles), tfl.toString(), to };
logger.log(logger.INFO, br.getKString(br.I_CLUSTER_TX_FILES, tmpargs));
GPacket gp = tfl.getGPacket();
gp.write(os);
os.flush();
String filename = null;
long filesize = 0L;
long lastmodtime = 0L;
for (int cnt = 0; cnt < numFiles; cnt++) {
filename = fileNames[cnt];
logger.log(logger.INFO, br.getKString(br.I_CLUSTER_TX_FILE, filename + " [" + Arrays.toString(tmpargs) + "]", to));
if (fileTransferShutdownOut) {
String emsg = br.getKString(br.W_CLUSTER_SERVICE_SHUTDOWN);
logger.log(logger.WARNING, emsg);
throw new BrokerException(emsg);
}
Map props = new HashMap();
InputStream is = callback.getFileInputStream(filename, targetBroker, props);
try {
filesize = ((Long) props.get("filesize")).longValue();
lastmodtime = ((Long) props.get("lastmodtime")).longValue();
ClusterTransferFileStartInfo tfs = ClusterTransferFileStartInfo.newInstance(uuid, module, myBrokerID, filename, filesize, lastmodtime);
gp = tfs.getGPacket();
gp.write(os);
os.flush();
digest.reset();
byte[] buf = new byte[FILE_TRANSFER_CHUNK_SIZE];
int totalread = 0;
int count;
while (totalread < filesize) {
if (fileTransferShutdownOut) {
String emsg = br.getKString(br.W_CLUSTER_SERVICE_SHUTDOWN);
logger.log(logger.WARNING, emsg);
throw new BrokerException(emsg);
}
count = 0;
try {
count = is.read(buf, 0, (int) Math.min(FILE_TRANSFER_CHUNK_SIZE, (filesize - totalread)));
} catch (IOException e) {
String emsg = br.getKString(br.E_FILE_READ, filename);
throw new BrokerException(emsg);
}
if (count < 0) {
String[] args = { String.valueOf(totalread), String.valueOf(filesize - totalread), filename };
String emsg = br.getKString(br.E_FILE_READ_EOF, args);
throw new BrokerException(emsg);
}
totalread += count;
os.write(buf, 0, count);
os.flush();
digest.update(buf, 0, count);
}
byte[] dg = digest.digest();
ClusterTransferFileEndInfo tfe = ClusterTransferFileEndInfo.newInstance(uuid, module, myBrokerID, filename, dg, ((cnt + 1) < numFiles));
gp = tfe.getGPacket();
gp.write(os);
os.flush();
} finally {
try {
is.close();
} catch (Exception e) {
}
}
}
if (numFiles > 0) {
InputStream sis = socket.getInputStream();
gp = GPacket.getInstance();
gp.read(sis);
if (gp.getType() != ProtocolGlobals.G_TRANSFER_FILE_END_ACK) {
String[] args = { ProtocolGlobals.getPacketTypeDisplayString(gp.getType()), to, ProtocolGlobals.getPacketTypeDisplayString(ProtocolGlobals.G_TRANSFER_FILE_END_ACK) };
String emsg = br.getKString(br.E_CLUSTER_UNEXPECTED_PACKET_FROM_1, args);
logger.log(logger.ERROR, emsg);
throw new BrokerException(emsg);
}
int status = ClusterTransferFileEndInfo.getReplyStatus(gp);
if (status != Status.OK) {
throw new BrokerException(ClusterTransferFileEndInfo.getReplyStatusReason(gp));
}
try {
gp = ClusterTransferFileEndInfo.getReplyAckGPacket(Status.OK, null);
gp.write(os);
os.flush();
} catch (Throwable t) {
if (DEBUG) {
logger.log(logger.INFO, "Exception in sending " + ProtocolGlobals.getPacketTypeDisplayString(ProtocolGlobals.G_TRANSFER_FILE_END_ACK_ACK) + " to " + to);
}
}
try {
sis.close();
} catch (Exception e) {
}
}
try {
socket.close();
} catch (Exception e) {
}
} catch (Throwable t) {
if (socket != null) {
try {
socket.close();
} catch (Exception e) {
}
}
StringBuilder buf = new StringBuilder();
if (fileNames != null) {
int len = fileNames.length;
for (int i = 0; i < len; i++) {
if (i > 0) {
buf.append(", ");
}
buf.append(fileNames[i]);
}
}
String emsg = br.getKString(br.X_CLUSTER_FILE_TX_FAIL, "[" + buf.toString() + "[" + uuid + "]]: " + ((t instanceof java.io.EOFException) ? "peer socket closed" : t.getMessage()), to);
logger.log(logger.ERROR, emsg);
if (t instanceof BrokerException) {
throw (BrokerException) t;
}
throw new BrokerException(emsg, t);
}
}
use of com.sun.messaging.jmq.jmsserver.multibroker.raptor.ClusterTransferFileEndInfo in project openmq by eclipse-ee4j.
the class FileTransferRunnable method run.
@Override
public void run() {
String from = remote + "[" + socket.getInetAddress() + "]";
try {
socket.setTcpNoDelay(true);
} catch (Exception e) {
logger.log(logger.WARNING, "Failed to set socket TCP_NODELAY in processing file transfer request: " + e);
}
try {
socket.setSoTimeout(timeout);
} catch (Exception e) {
logger.log(logger.WARNING, "Failed to set socket timeout in processing file transfer request: " + e);
}
try {
InputStream is = socket.getInputStream();
GPacket gp = GPacket.getInstance();
gp.read(is);
if (gp.getType() != ProtocolGlobals.G_TRANSFER_FILE_LIST) {
String[] emsg = { ProtocolGlobals.getPacketTypeDisplayString(gp.getType()), from, ProtocolGlobals.getPacketTypeDisplayString(ProtocolGlobals.G_TRANSFER_FILE_LIST) };
logger.log(logger.ERROR, br.getKString(br.E_CLUSTER_UNEXPECTED_PACKET_FROM_1, emsg));
try {
socket.close();
} catch (Exception e) {
/* ignore */
}
return;
}
ClusterTransferFileListInfo tfl = ClusterTransferFileListInfo.newInstance(gp);
String uuid = tfl.getUUID();
String pendingUUID = parent.pendingFileTransfers.get(remote);
if (pendingUUID == null || !pendingUUID.startsWith(tfl.getUUID())) {
logger.log(logger.ERROR, br.getKString(br.E_CLUSTER_RECEIVED_UNKNOW_FILE_TX_LIST, ProtocolGlobals.getPacketTypeDisplayString(gp.getType()) + tfl, remote));
try {
socket.close();
} catch (Exception e) {
}
return;
}
if (!tfl.getModule().equals(FileTransferCallback.STORE)) {
logger.log(logger.ERROR, br.getKString(br.E_CLUSTER_UNEXPECTED_PACKET_FROM, ProtocolGlobals.getPacketTypeDisplayString(gp.getType()) + tfl.toString(true), from));
try {
socket.close();
} catch (Exception e) {
}
return;
}
FileTransferCallback callback = (FileTransferCallback) Globals.getStore();
int numFiles = tfl.getNumFiles();
for (int cnt = 0; cnt < numFiles; cnt++) {
if (parent.fileTransferShutdownIn) {
String emsg = br.getKString(br.W_CLUSTER_SERVICE_SHUTDOWN);
logger.log(logger.WARNING, emsg);
throw new BrokerException(emsg);
}
gp.read(is);
if (gp.getType() != ProtocolGlobals.G_TRANSFER_FILE_START) {
String[] emsg = { ProtocolGlobals.getPacketTypeDisplayString(gp.getType()), from, ProtocolGlobals.getPacketTypeDisplayString(ProtocolGlobals.G_TRANSFER_FILE_START) };
logger.log(logger.ERROR, br.getKString(br.E_CLUSTER_UNEXPECTED_PACKET_FROM_1, emsg));
try {
socket.close();
} catch (Exception e) {
}
return;
}
ClusterTransferFileStartInfo tfs = ClusterTransferFileStartInfo.newInstance(gp);
if (!tfs.getModule().equals(FileTransferCallback.STORE)) {
logger.log(logger.ERROR, br.getKString(br.E_CLUSTER_UNEXPECTED_PACKET_FROM, ProtocolGlobals.getPacketTypeDisplayString(gp.getType()) + tfs.toString(true), from));
try {
socket.close();
} catch (Exception e) {
}
return;
}
if (!tfs.getBrokerID().equals(tfl.getBrokerID())) {
logger.log(logger.ERROR, br.getKString(br.E_CLUSTER_UNEXPECTED_PACKET_FROM, ProtocolGlobals.getPacketTypeDisplayString(gp.getType()) + tfs.toString(true), from));
try {
socket.close();
} catch (Exception e) {
}
return;
}
String tmpfile = tfs.getFileName() + ".tmp";
ClusterTransferFileEndInfo fte = null;
boolean success = false;
OutputStream os = callback.getFileOutputStream(tmpfile, tfs.getBrokerID(), uuid, cnt == 0, remote);
try {
digest.reset();
long size = tfs.getFileSize();
byte[] buf = new byte[parent.FILE_TRANSFER_CHUNK_SIZE];
int totalread = 0;
int count;
while (totalread < size) {
if (parent.fileTransferShutdownIn) {
String emsg = br.getKString(br.W_CLUSTER_SERVICE_SHUTDOWN);
logger.log(logger.WARNING, emsg);
throw new BrokerException(emsg);
}
count = 0;
try {
count = is.read(buf, 0, (int) Math.min(parent.FILE_TRANSFER_CHUNK_SIZE, (size - totalread)));
} catch (IOException e) {
logger.log(logger.ERROR, br.getKString(br.E_CLUSTER_FILE_TX_READ, from + ": " + e));
try {
socket.close();
} catch (Exception e1) {
}
return;
}
if (count < 0) {
String[] args = { String.valueOf(totalread), String.valueOf(size - totalread), from };
logger.log(logger.ERROR, br.getKString(br.E_CLUSTER_FILE_TX_EOF, args));
try {
socket.close();
} catch (Exception e) {
}
return;
}
totalread += count;
os.write(buf, 0, count);
digest.update(buf, 0, count);
}
String[] args = { String.valueOf(size), tfs.getFileName(), from };
logger.log(logger.INFO, br.getKString(br.I_FILE_TX_COMPLETE, args));
gp = GPacket.getInstance();
gp.read(is);
if (gp.getType() != ProtocolGlobals.G_TRANSFER_FILE_END) {
String[] emsg = { ProtocolGlobals.getPacketTypeDisplayString(gp.getType()), from, ProtocolGlobals.getPacketTypeDisplayString(ProtocolGlobals.G_TRANSFER_FILE_END) };
logger.log(logger.ERROR, br.getKString(br.E_CLUSTER_UNEXPECTED_PACKET_FROM_1, emsg));
try {
socket.close();
} catch (Exception e) {
}
return;
}
fte = ClusterTransferFileEndInfo.newInstance(gp);
if (!Arrays.equals(digest.digest(), fte.getDigest())) {
logger.log(logger.ERROR, br.getKString(br.E_CLUSTER_FILE_TX_DIGEST_MISMATCH, tfs.getFileName(), from));
try {
socket.close();
} catch (Exception e) {
}
return;
}
os.close();
logger.log(logger.INFO, br.getKString(br.I_FILE_TX_SUCCESS, tfs.getFileName(), from));
callback.doneTransfer(tmpfile, tfs.getFileName(), tfs.getBrokerID(), tfs.getLastModifiedTime(), true, remote);
success = true;
} finally {
if (!success) {
// cleanup
try {
os.close();
} catch (Exception e) {
}
callback.doneTransfer(tmpfile, tfs.getFileName(), tfs.getBrokerID(), tfs.getLastModifiedTime(), false, remote);
}
}
if (fte.hasMoreFiles() != ((cnt + 1) < numFiles)) {
String[] args = { String.valueOf(numFiles), from, String.valueOf(cnt + 1), String.valueOf(fte.hasMoreFiles()) };
String emsg = br.getKString(br.E_CLUSTER_FILE_TX_NUMFILES, args);
logger.log(logger.ERROR, emsg);
throw new BrokerException(emsg);
}
}
if (numFiles > 0) {
callback.allDoneTransfer(tfl.getBrokerID(), tfl.getUUID(), remote);
OutputStream sos = socket.getOutputStream();
gp = ClusterTransferFileEndInfo.getReplyGPacket(Status.OK, (String) null);
gp.write(sos);
sos.flush();
try {
gp = GPacket.getInstance();
gp.read(is);
if (gp.getType() != ProtocolGlobals.G_TRANSFER_FILE_END_ACK_ACK) {
String[] args = { ProtocolGlobals.getPacketTypeDisplayString(gp.getType()), from, ProtocolGlobals.getPacketTypeDisplayString(ProtocolGlobals.G_TRANSFER_FILE_END_ACK_ACK) };
String emsg = br.getKString(br.E_CLUSTER_UNEXPECTED_PACKET_FROM_1, args);
logger.log(logger.ERROR, emsg);
throw new BrokerException(emsg);
}
} catch (Throwable t) {
if (parent.DEBUG) {
logger.log(logger.INFO, "Exception in receiving " + ProtocolGlobals.getPacketTypeDisplayString(ProtocolGlobals.G_TRANSFER_FILE_END_ACK_ACK) + " from " + from + " for tranfer files of broker " + tfl.getBrokerID() + ": " + t.getMessage());
}
}
try {
is.close();
} catch (Exception e) {
}
try {
sos.close();
} catch (Exception e) {
}
try {
socket.close();
} catch (Exception e) {
}
}
} catch (Throwable t) {
try {
socket.close();
} catch (Exception e) {
}
logger.logStack(logger.ERROR, br.getKString(br.E_CLUSTER_PROCESS_FILE_TX_REQUEST, from), t);
} finally {
es.shutdownNow();
}
}
Aggregations