jadex.base.service.awareness.discovery.message.MessageDiscoveryAgent Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of jadex-platform-base Show documentation
Show all versions of jadex-platform-base Show documentation
The Jadex platform base package contains
functionality useful for constructing platforms.
The newest version!
package jadex.base.service.awareness.discovery.message;
import jadex.base.service.awareness.discovery.DiscoveryAgent;
import jadex.base.service.awareness.discovery.ReceiveHandler;
import jadex.base.service.awareness.discovery.SendHandler;
import jadex.bridge.ComponentIdentifier;
import jadex.bridge.ComponentTerminatedException;
import jadex.bridge.IComponentIdentifier;
import jadex.bridge.IComponentStep;
import jadex.bridge.IInternalAccess;
import jadex.bridge.fipa.SFipa;
import jadex.bridge.service.annotation.Service;
import jadex.bridge.service.types.awareness.AwarenessInfo;
import jadex.bridge.service.types.awareness.IAwarenessManagementService;
import jadex.bridge.service.types.message.MessageType;
import jadex.commons.SUtil;
import jadex.commons.future.DefaultResultListener;
import jadex.commons.future.IFuture;
import jadex.micro.AbstractMessageHandler;
import jadex.micro.annotation.Agent;
import jadex.micro.annotation.Implementation;
import jadex.micro.annotation.ProvidedService;
import jadex.micro.annotation.ProvidedServices;
import java.util.HashMap;
import java.util.Map;
/**
* Discovery agent that is based on message receipt.
*
* The message service announces the sender of each incoming
* message to the IMessageAwarenessService of this agent.
*
* The agent will announce the underlying platform and uses
* ping messages to its rms to check if it is still present.
*/
@Agent
@ProvidedServices(@ProvidedService(type=IMessageAwarenessService.class,
implementation=@Implementation(expression="$component.getPojoAgent()")))
@Service
public class MessageDiscoveryAgent extends DiscoveryAgent implements IMessageAwarenessService
{
//-------- attributes --------
/** The map of announced component identifiers. */
protected Map announcements = new HashMap();
//-------- service methods --------
/**
* Announce a potentially new component identifier.
* @param cid The component identifier.
*/
public IFuture announceComponentIdentifier(IComponentIdentifier ccid)
{
// Only handle platforms
IComponentIdentifier cid = ccid.getRoot();
// Return in case of self message.
if(getMicroAgent().getComponentIdentifier().getRoot().equals(cid))
return IFuture.DONE;
// Do not start another check if already contained
if(announcements.containsKey(cid))
{
// Update time
announcements.put(cid, System.currentTimeMillis());
}
else
{
// System.out.println("enter: "+cid);
performAnnouncements(cid);
}
return IFuture.DONE;
}
//-------- internal methods --------
/**
* Perform continuous announcements until no ping answers are received any longer.
*/
protected void performAnnouncements(final IComponentIdentifier cid)
{
AwarenessInfo info = new AwarenessInfo(cid.getRoot(), AwarenessInfo.STATE_ONLINE, getDelay(), null, null, null);
announcements.put(cid, System.currentTimeMillis());
announceAwareness(info);
// Check alive via sending ping message before delay is due
long del = (long)(getDelay()-((double)getDelay())*0.1);
// System.out.println("performing: "+cid+" "+del+" "+System.currentTimeMillis());
doWaitFor(del, new IComponentStep()
{
public IFuture execute(IInternalAccess ia)
{
Map msg = new HashMap();
ComponentIdentifier rec = new ComponentIdentifier("rms@"+cid.getPlatformName(), cid.getAddresses());
msg.put(SFipa.RECEIVERS, new IComponentIdentifier[]{rec});
msg.put(SFipa.CONTENT, "ping");
msg.put(SFipa.PERFORMATIVE, SFipa.QUERY_IF);
msg.put(SFipa.CONVERSATION_ID, SUtil.createUniqueId("msg_dis"));
getMicroAgent().sendMessageAndWait(msg, SFipa.FIPA_MESSAGE_TYPE, new AbstractMessageHandler(5000, true)
{
public void handleMessage(Map msg, MessageType type)
{
// System.out.println("received reply: "+msg);
performAnnouncements(cid);
}
public void timeoutOccurred()
{
// System.out.println("Received no ping reply, removed: "+cid);
announcements.remove(cid);
}
});
return IFuture.DONE;
}
});
}
//-------- template methods (nop for relay) --------
/**
* Create the send handler.
*/
public SendHandler createSendHandler()
{
return null;
}
/**
* Create the receive handler.
*/
public ReceiveHandler createReceiveHandler()
{
return null;
}
/**
* (Re)init sending/receiving ressource.
*/
protected void initNetworkRessource()
{
}
/**
* Terminate sending/receiving ressource.
*/
protected void terminateNetworkRessource()
{
}
/**
* Announce newly arrived awareness info to management service.
*/
public void announceAwareness(final AwarenessInfo info)
{
// System.out.println("announcing: "+info);
if(info.getSender()!=null)
{
if(info.getSender().equals(getRoot()))
received_self = true;
// System.out.println(System.currentTimeMillis()+" "+getComponentIdentifier()+" received: "+info.getSender());
IFuture msfut = getMicroAgent().getRequiredService("management");
msfut.addResultListener(new DefaultResultListener(getMicroAgent().getLogger())
{
public void resultAvailable(IAwarenessManagementService ms)
{
ms.addAwarenessInfo(info).addResultListener(new DefaultResultListener(getMicroAgent().getLogger())
{
public void resultAvailable(Boolean result)
{
// nothing to do
}
public void exceptionOccurred(Exception exception)
{
if(!(exception instanceof ComponentTerminatedException))
super.exceptionOccurred(exception);
}
});
}
public void exceptionOccurred(Exception exception)
{
if(!(exception instanceof ComponentTerminatedException))
super.exceptionOccurred(exception);
}
});
}
}
}