DS-Lab / src / main / java / dslab / monitoring / MonitoringClient.java
MonitoringClient.java
Raw
package dslab.monitoring;

import dslab.protocol.Message;
import dslab.util.TransferServerConfig;

import java.io.Closeable;
import java.io.IOException;
import java.net.*;
import java.util.logging.Logger;

import static java.util.logging.Level.SEVERE;

public class MonitoringClient implements Closeable {

    private static final Logger LOG = Logger.getLogger(MonitoringClient.class.getSimpleName());
    private final DatagramSocket socket;
    private final InetAddress monitoringAddress;
    private final int monitoringPort;
    private final String MY_IP;
    private final int MY_PORT;

    /**
     * The client side representation of the monitoring server. This class essentially
     * wraps the transfer server end of the UDP channel between the transfer server and the
     * monitoring server
     */
    public MonitoringClient(TransferServerConfig config) throws SocketException, UnknownHostException {

        socket = new DatagramSocket();

        //Get these values in the constructor so we fail fast
        monitoringAddress = InetAddress.getByName(config.monitoringHost());
        monitoringPort = config.monitoringPort();

        MY_IP = InetAddress.getLocalHost().getHostAddress();
        MY_PORT = config.tcpPort();
    }

    /**
     * Reports sent messages to the transfer server. The assignment doesn't specify if a message with
     * two recipients counts as two messages or as one. If the goal is to detect abuse, as indicated
     * in the assignment text, then it makes more sense to count it as two; so that's what we do here
     * @param message to report to the monitoring server as having been sent
     */
    public void report(Message message) {

        var report = MY_IP + ":" + MY_PORT + " " + message.getSender();
        LOG.info("Reporting to monitoring server: " + report);

        byte[] buffer = report.getBytes();
        var packet = new DatagramPacket(buffer, buffer.length, monitoringAddress, monitoringPort);
        try {
            //Send packet n times if the message has n recipients. This is stupid but the spec demands it
            for(var i = 1; i <= message.getRecipients().size(); ++i)
                socket.send(packet);

        } catch (IOException e) {
            LOG.log(SEVERE, "Unable to report to monitoring server", e);
        }
    }

    public void close() {
        socket.close();
    }
}