/* * To change this license header, choose License Headers in Project Properties. * To change this template file, choose Tools | Templates * and open the template in the editor. */ package org.pieShare.pieTools.piePlate.task; import java.net.InetSocketAddress; import org.pieShare.pieTools.piePlate.model.message.loopHoleMessages.LoopHoleAckMessage; import org.pieShare.pieTools.piePlate.model.message.loopHoleMessages.LoopHoleCompleteMessage; import org.pieShare.pieTools.piePlate.model.message.loopHoleMessages.LoopHoleConnectionMessage; import org.pieShare.pieTools.piePlate.model.message.loopHoleMessages.LoopHolePunchMessage; import org.pieShare.pieTools.piePlate.service.loophole.api.ILoopHoleFactory; import org.pieShare.pieTools.piePlate.service.loophole.api.ILoopHoleService; import org.pieShare.pieTools.pieUtilities.service.beanService.IBeanService; import org.pieShare.pieTools.pieUtilities.service.pieExecutorService.api.task.IPieEventTask; import org.pieShare.pieTools.pieUtilities.service.pieLogger.PieLogger; /** * * @author Richard */ public class LoopHoleConnectionTask implements IPieEventTask<LoopHoleConnectionMessage> { private LoopHoleConnectionMessage msg; private ILoopHoleService loopHoleService; private boolean isWaitingForAck = false; private boolean stop = false; private String host; private int port; private IBeanService beanService; private ILoopHoleFactory loopHoleFactory; @Override public void setEvent(LoopHoleConnectionMessage msg) { this.msg = msg; } public void setLoopHoleFactory(ILoopHoleFactory loopHoleFactory) { this.loopHoleFactory = loopHoleFactory; } public IBeanService getBeanService() { return beanService; } public void setBeanService(IBeanService beanService) { this.beanService = beanService; } public void setMsg(LoopHoleConnectionMessage msg) { this.msg = msg; } @Override public void run() { LoopHoleAckMessage ackMsg = beanService.getBean(LoopHoleAckMessage.class); ackMsg.setLocalLoopID(msg.getLocalLoopID()); loopHoleService = loopHoleFactory.getLoopHoleService(msg.getLocalLoopID()); loopHoleService.sendToServer(ackMsg); int endpoint = 0; while (!stop) { if (endpoint == 0) { host = msg.getClientPrivateIP(); port = msg.getClientPrivatePort(); endpoint++; } else { host = msg.getClientPublicIP(); port = msg.getClientPublicPort(); endpoint = 0; } LoopHolePunchMessage punchMsg = beanService.getBean(LoopHolePunchMessage.class); punchMsg.setTo(msg.getFromId()); punchMsg.setFrom(loopHoleFactory.getClientID()); punchMsg.setName(loopHoleService.getName()); punchMsg.setLocalLoopID(msg.getClientLocalLoopID()); punchMsg.setClientLocalLoopID(msg.getLocalLoopID()); loopHoleService.addInWaitFromAckQueu(msg.getFromId(), this); loopHoleService.send(punchMsg, new InetSocketAddress(host, port)); isWaitingForAck = true; try { Thread.sleep(5000); } catch (InterruptedException ex) { PieLogger.error(this.getClass(), "Error while waiting for ACK", ex); } isWaitingForAck = false; loopHoleService.removeTaskFromAckWaitQueue(msg.getFromId()); } } public void ackArrived() { if (isWaitingForAck) { stop = true; InetSocketAddress address = new InetSocketAddress(host, port); LoopHoleCompleteMessage completeMessage = beanService.getBean(LoopHoleCompleteMessage.class); completeMessage.setLocalLoopID(msg.getClientLocalLoopID()); completeMessage.setClientLocalLoopID(msg.getLocalLoopID()); loopHoleService.send(completeMessage, address); loopHoleService.newClientAvailable(address); } } }