com.almende.eve.ggdemo.DAALampAgent.java Source code

Java tutorial

Introduction

Here is the source code for com.almende.eve.ggdemo.DAALampAgent.java

Source

/*
 * Copyright: Almende B.V. (2014), Rotterdam, The Netherlands
 * License: The Apache Software License, Version 2.0
 */
package com.almende.eve.ggdemo;

import java.io.IOException;
import java.net.URI;
import java.util.List;

import org.joda.time.DateTime;

import com.almende.eve.algorithms.DAA;
import com.almende.eve.algorithms.DAAValueBean;
import com.almende.eve.algorithms.TrickleRPC;
import com.almende.eve.protocol.jsonrpc.annotation.Name;
import com.almende.eve.protocol.jsonrpc.annotation.Namespace;
import com.almende.eve.protocol.jsonrpc.annotation.Optional;
import com.almende.eve.protocol.jsonrpc.formats.JSONRPCException;
import com.almende.eve.protocol.jsonrpc.formats.Params;
import com.almende.util.URIUtil;
import com.almende.util.jackson.JOM;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.node.ObjectNode;

/**
 * The Class DAALampAgent.
 */
public class DAALampAgent extends AbstractLampAgent {
    private DAA lampCnt = new DAA();
    private DAA onCnt = new DAA();

    private TrickleRPC trickle = null;
    private double percent = 0.0;

    /*
     * (non-Javadoc)
     * @see
     * com.almende.eve.ggdemo.LampAgent#handleGoal(com.almende.eve.ggdemo.Goal,
     * java.lang.String)
     */
    @Override
    public void handleGoal(Goal goal, URI sender) throws JSONRPCException, JsonProcessingException, IOException {
        if (neighbours == null) {
            neighbours = getNeighbours();
        }
        Goal oldgoal = getState().get("goal", Goal.class);
        if (oldgoal != null && oldgoal.getId().equals(goal.getId())) {
            // EARLY exist, seen this goal before.
            return;
        }
        getState().put("goal", goal);

        percent = goal.getGoalPct();
        for (String neighbour : neighbours) {
            ObjectNode params = JOM.createObjectNode();
            params.set("goal", JOM.getInstance().valueToTree(goal));
            call(URIUtil.create(neighbour), "handleGoal", params, null);
        }
    }

    private void setOnValue(double value) {
        onCnt.setNewValue(value);
    }

    public void scheduleLamps() {
        checkLamps();
        schedule("scheduleLamps", null, 1000 + Math.round(Math.random() * 5000));
    }

    private void checkLamps() {
        long requiredOn = Math.round((percent * lampCnt.computeSum()) / 100);
        long diff = requiredOn - Math.round(onCnt.computeSum());
        System.out.println(
                getId() + ": diff:" + diff + "/" + requiredOn + " on total:" + Math.round(lampCnt.computeSum()));
        if (diff > 0) {
            if (!super.isOn()) {
                lampOn();
                setOnValue(1.0);
                trickle.reset();
                System.out.print("!");
            }
        } else if (diff < 0) {
            if (super.isOn()) {
                lampOff();
                setOnValue(0.0);
                trickle.reset();
                System.out.print(".");
            }
        }
    }

    @Override
    public void create(List<String> neighbours, Integer stepSize) throws JSONRPCException, IOException {
        super.create(neighbours, stepSize);
        final ObjectNode config = JOM.createObjectNode();
        config.put("width", 1000);
        config.put("initialTTL", 10);
        config.put("evictionFactor", 20);

        config.put("intervalFactor", 5);
        config.put("intervalMin", 200);
        config.put("redundancyFactor", 999);

        lampCnt.configure(config);
        lampCnt.setNewValue(1.0);

        onCnt.configure(config);
        onCnt.setNewValue(super.isOn() ? 1.0 : 0.0);

        final List<String> nbs = neighbours;
        trickle = new TrickleRPC(config, getScheduler(), new Runnable() {
            @Override
            public void run() {
                //checkLamps();
                final long delay = (long) (trickle.getDelay() * 3.2);
                lampCnt.getLocalValue().setTTL(DateTime.now().plus(delay).getMillis());
                onCnt.getLocalValue().setTTL(DateTime.now().plus(delay).getMillis());
            }
        }, new Runnable() {
            @Override
            public void run() {
                for (final String neighbour : nbs) {
                    Params params = new Params();
                    params.add("nofLamps", lampCnt.getCurrentEstimate());
                    params.add("nofOn", onCnt.getCurrentEstimate());
                    try {
                        call(URIUtil.create(neighbour), "daaReceive", params);
                    } catch (IOException e) {
                    }
                }
            }
        });
        scheduleLamps();
    }

    /**
     * Gets the trickle.
     *
     * @return the trickle
     */
    @Namespace("*")
    public TrickleRPC getTrickle() {
        return trickle;
    }

    /**
     * Daa receive.
     *
     * @param nofLamps
     *            the nof lamps
     * @param nofOn
     *            the nof on
     * @throws JsonProcessingException
     *             the json processing exception
     */
    public void daaReceive(@Name("nofLamps") @Optional DAAValueBean nofLamps,
            @Name("nofOn") @Optional DAAValueBean nofOn) throws JsonProcessingException {
        if (nofLamps == null) {
            nofLamps = lampCnt.getCurrentEstimate();
        }
        if (nofOn == null) {
            nofOn = onCnt.getCurrentEstimate();
        }
        double oldNofLamps = 0.0;
        if (lampCnt.getCurrentEstimate() != null) {
            oldNofLamps = lampCnt.getCurrentEstimate().computeSum();
        }
        double oldNofOn = 0.0;
        if (onCnt.getCurrentEstimate() != null) {
            oldNofOn = onCnt.getCurrentEstimate().computeSum();
        }
        lampCnt.receive(nofLamps);
        onCnt.receive(nofOn);
        if (trickle != null) {
            if (oldNofLamps != lampCnt.getCurrentEstimate().computeSum()
                    || oldNofOn != onCnt.getCurrentEstimate().computeSum()) {
                trickle.reset();
            } else {
                trickle.incr();
            }
        }
    }
}