Menu

Using external messaging with JADE

Help
2008-04-22
2018-03-20
  • Vidar Engmo

    Vidar Engmo - 2008-04-22

    I my name is Vidar and I am trying to use JADE for the message flow in robocode. It is more of a project, just to find out how this works. The problem is that it is not possible to send information from a JADE agent to a robocode agent. When the robocode agent starts it creates its JADE agent counterpart. It is no problem to send objects to the JADE agent from robocode using putO2AObject, but trying to communicate from JADE to robocode seems to be impossible. I have sent an argument object when creating the JADE agent. But when trying to parse the object into its original form it protests.

    Agent container Container-2@VIDARLTNEW is ready.

    .Hallo! Soldier-agent SoldierRobot (2)@VIDARLTNEW:1099/JADE is ready.
    *** Uncaught Exception for agent SoldierRobot (2) ***
    java.lang.ClassCastException: exercise.Contract cannot be cast to exercise.Contr
    act
    at exercise.Soldier.setup(Soldier.java:26)
    at jade.core.Agent$ActiveLifeCycle.init(Agent.java:1452)
    at jade.core.Agent.run(Agent.java:1398)
    at java.lang.Thread.run(Unknown Source)
    ERROR: Agent SoldierRobot (2) died without being properly terminated !!!

    Code from class Soldier (JADE agent): ***********
    public class Soldier extends Agent{

    private static final long serialVersionUID = 1L;
    private Contract contract;
    
    // Put Agent initializations here
    protected void setup(){
        // Printout a welcome message
        System.out.println("Hallo! Soldier-agent "+getAID().getName()+" is ready.");
    
        // Initial values
        Object args[] = getArguments();
        contract = (Contract)args[0];   ******************** THIS IS THE PROBLEM **********************
    
        // Accept objects through the object-to-agent communication
        // channel, with a maximum size of 10 queued objects
        setEnabledO2ACommunication(true, 10);
    
        // Register the soldier-hiring service in the yellow pages
        DFAgentDescription dfd = new DFAgentDescription();
        dfd.setName(getAID());
        ServiceDescription sd = new ServiceDescription();
        sd.setType("soldier-available");
        sd.setName("JADE-soldier-trading");
        dfd.addServices(sd);
        try {
          DFService.register(this, dfd);
        }
        catch (FIPAException fe) {
          fe.printStackTrace();
        }
    
        addBehaviour(new OfferRequestsServer());
        addBehaviour(new OfferAcceptedServer());
        addBehaviour(new RobotMessageServer());
    }
        etc.
    

    Code from class SoldierRobot: ***********
    public class SoldierRobot extends TeamRobot {

    // Variables for JADE control
    private jade.core.Runtime rt;
    private jade.wrapper.ContainerController cc;
    private jade.wrapper.AgentController ac;
    private Contract contract;
    
    public void run(){
        // Start JADE AGENT here
        startJADE();
    
        // Setup Robot here 
        while(true){
            ahead(100);
            setTurnRadarRight(360);
            turnLeft(45);
            execute();
        }
    }
    
    public void startJADE(){
        rt = jade.core.Runtime.instance();
        jade.core.Profile p = new jade.core.ProfileImpl();
        cc = rt.createAgentContainer(p);
        contract = new Contract();
        try {
            ac = cc.createNewAgent(getName(), "exercise.Soldier", new Object[]{contract}); ******* contract is sent to JADE here ********
            ac.start();
        } catch (StaleProxyException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
    }
    

    Hope someone can help me!

    Vidar Engmo

     
    • Flemming N. Larsen

      Hi Vidar,

      It is really hard to tell, especially when I cannot see how the Contract is declared. Anyways, I guess the problem (without knowing for sure) that the problem lies in:

      Object args[] = getArguments();

      If this is arguments like the ones for e.g. 'public static void main(String[] args)', then your 'args' will be Strings, not Contracts. Then you are allowed to assign the define args[] as Objects with the line above, as String are Objects.

      But when we get to this line:

      contract = (Contract)args[0];

      .. then it will be a problem, as it does not make sense to typecast a String to a Contract.


      The solution for your problem might be to serialize your Contract object into a string, e.g. using ByteArrayOutputStream and ObjectOutputStream (for outputting the Contract), and then put this into your String for arg[0]. Then you replace your 'contract = (Contract)args[0];' with a "decoder" using the oposite technique for translating a string into a Contract using ByteArrayInputStream and ObjectInputStream.

      So in short. If your args infact are Strings (you should check this), then you should code your Contract object to a String for the arg[0], and then decode the String to a Contract on the other side.

      Hope this makes sense?

       
    • Vidar Engmo

      Vidar Engmo - 2008-04-23

      The whole point was to send a reference to a object. So that the Robocode and the JADE agent could share a memory space. I have tried setting up a test. This test works fine. No changes in Soldier.java.. And it works, I can use it as a refernce and both classes kan change the variables within. So what happens, in the real case the object is turned into a string, and in the test case it is not.

      TEST CODE ************
      public class Mytest02 {

      // Variables for JADE control
      private jade.core.Runtime rt;
      private jade.wrapper.ContainerController cc;
      private jade.wrapper.AgentController ac;
      private static Contract contract;
      
      public Mytest02(){
          startJADE();
      }
      
      public void startJADE(){
          rt = jade.core.Runtime.instance();
          jade.core.Profile p = new jade.core.ProfileImpl();
          cc = rt.createAgentContainer(p);
          contract = new Contract();
          try {
              ac = cc.createNewAgent("Soldier1", "exercise.Soldier", new Object[]{contract});
              ac.start();
          } catch (StaleProxyException e) {
              // TODO Auto-generated catch block
              e.printStackTrace();
          }
      }
      
      public static void myprint(){
          System.out.println("The enemy is: "+ contract.getEnemy());
      }
      
      public static void main(String[] args) {
          new Mytest02();
      
          while(true){
              myprint();
              try {
                  Thread.sleep(1000);
              } catch (InterruptedException e) {
                  // TODO Auto-generated catch block
                  e.printStackTrace();
              }
          }
      }
      

      }

      **** Contract code *******

      public class Contract {

      private boolean hired = false;
      private String enemy;
      
      public boolean isHired() {
          return hired;
      }
      public void setHired(boolean hired) {
          this.hired = hired;
      }
      public String getEnemy() {
          return enemy;
      }
      public void setEnemy(String enemy) {
          this.enemy = enemy;
      }
      

      }

       
      • Flemming N. Larsen

        Now I understand what you are trying to do. I am not sure if you receive a String as arg[0] from the Robocode agent you listed in your previous message, as you received this error message:

        *** Uncaught Exception for agent SoldierRobot (2) ***
        java.lang.ClassCastException: exercise.Contract cannot be cast to exercise.Contract at exercise

        This tells you that you try to typecast exercise.Contract into exercise.Contract which cannot be done. Atually, this should be possible to do. Perhaps the Contract needs to implement java.io.Serializable?

        Also, as this is a problem with JADE, I would get help from the JADE developers, and ask them why to get the:

        java.lang.ClassCastException: exercise.Contract cannot be cast to exercise.Contract at exercise

        .. when you are typecasting between the same class?

        Have you tried to clean and rebuild your stuff? It might be a trivial building/runtime problem?

         
  • Nikos

    Nikos - 2018-03-20

    Hi Vidar,
    Did you manage to develop a competitive JADE agent for robocode?
    I am asking because I also aim to start such a small project...
    Thank you,
    Nikos

     

Log in to post a comment.