/*
 *  Copyright 2016-present Open Networking Laboratory
 *
 *  Licensed under the Apache License, Version 2.0 (the "License");
 *  you may not use this file except in compliance with the License.
 *  You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 *  Unless required by applicable law or agreed to in writing, software
 *  distributed under the License is distributed on an "AS IS" BASIS,
 *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 *  See the License for the specific language governing permissions and
 *  limitations under the License.
 */

package org.onosproject.ui.impl.topo.util;

import org.onosproject.net.Link;
import org.onosproject.net.LinkKey;
import org.onosproject.net.statistic.Load;
import org.onosproject.ui.topo.BiLink;
import org.onosproject.ui.topo.LinkHighlight;
import org.onosproject.ui.topo.LinkHighlight.Flavor;
import org.onosproject.ui.topo.Mod;
import org.onosproject.ui.topo.TopoUtils.Magnitude;
import org.onosproject.ui.topo.TopoUtils.ValueLabel;

import java.util.HashSet;
import java.util.Set;

import static org.onosproject.ui.topo.LinkHighlight.Flavor.NO_HIGHLIGHT;
import static org.onosproject.ui.topo.LinkHighlight.Flavor.PRIMARY_HIGHLIGHT;
import static org.onosproject.ui.topo.LinkHighlight.Flavor.SECONDARY_HIGHLIGHT;
import static org.onosproject.ui.topo.TopoUtils.formatBytes;
import static org.onosproject.ui.topo.TopoUtils.formatClippedBitRate;
import static org.onosproject.ui.topo.TopoUtils.formatFlows;
import static org.onosproject.ui.topo.TopoUtils.formatPacketRate;

/**
 * Representation of a link and its inverse, and associated traffic data.
 * This class understands how to generate the appropriate
 * {@link LinkHighlight}s for showing traffic data on the topology view.
 */
public class TrafficLink extends BiLink {
    private static final Mod PORT_TRAFFIC_GREEN = new Mod("port-traffic-green");
    private static final Mod PORT_TRAFFIC_YELLOW = new Mod("port-traffic-yellow");
    private static final Mod PORT_TRAFFIC_ORANGE = new Mod("port-traffic-orange");
    private static final Mod PORT_TRAFFIC_RED = new Mod("port-traffic-red");

    private static final String EMPTY = "";

    private long bytes = 0;
    private long rate = 0;
    private long flows = 0;
    private Flavor taggedFlavor = NO_HIGHLIGHT;
    private boolean hasTraffic = false;
    private boolean isOptical = false;
    private boolean antMarch = false;
    private Set<Mod> mods = new HashSet<>();

    /**
     * Constructs a traffic link for the given key and initial link.
     *
     * @param key  canonical key for this traffic link
     * @param link first link
     */
    public TrafficLink(LinkKey key, Link link) {
        super(key, link);
    }

    /**
     * Sets the optical flag to the given value.
     *
     * @param b true if an optical link
     * @return self, for chaining
     */
    public TrafficLink optical(boolean b) {
        isOptical = b;
        return this;
    }

    /**
     * Sets the ant march flag to the given value.
     *
     * @param b true if marching ants required
     * @return self, for chaining
     */
    public TrafficLink antMarch(boolean b) {
        antMarch = b;
        return this;
    }

    /**
     * Tags this traffic link with the flavor to be used in visual rendering.
     *
     * @param flavor the flavor to tag
     * @return self, for chaining
     */
    public TrafficLink tagFlavor(Flavor flavor) {
        taggedFlavor = flavor;
        return this;
    }

    /**
     * Tags this traffic link with the mods to be used in visual rendering.
     *
     * @param mods the mods to tag on this link
     * @return self, for chaining
     */
    public TrafficLink tagMods(Set<Mod> mods) {
        if (mods != null) {
            this.mods.addAll(mods);
        }
        return this;
    }

    /**
     * Adds load statistics, marks the traffic link as having traffic.
     *
     * @param load load to add
     */
    public void addLoad(Load load) {
        addLoad(load, 0);
    }

    /**
     * Adds load statistics, marks the traffic link as having traffic, if the
     * load {@link Load#rate rate} is greater than the given threshold
     * (expressed in bytes per second).
     *
     * @param load      load to add
     * @param threshold threshold to register traffic
     */
    public void addLoad(Load load, double threshold) {
        if (load != null) {
            this.hasTraffic = hasTraffic || load.rate() > threshold;
            this.bytes += load.latest();
            this.rate += load.rate();
        }
    }

    /**
     * Adds the given count of flows to this traffic link.
     *
     * @param count count of flows
     */
    public void addFlows(int count) {
        this.flows += count;
    }

    @Override
    public LinkHighlight highlight(Enum<?> type) {
        StatsType statsType = (StatsType) type;
        switch (statsType) {
            case FLOW_COUNT:
                return highlightForFlowCount();

            case FLOW_STATS:
            case PORT_STATS:
            case PORT_PACKET_STATS:
                return highlightForStats(statsType);

            case TAGGED:
                return highlightForTagging();

            default:
                throw new IllegalStateException("unexpected case: " + statsType);
        }
    }

    private LinkHighlight highlightForStats(StatsType type) {
        ValueLabel vl = null;
        Mod m = null;

        // based on the type of stats, need to determine the label and "color"...
        switch (type) {
            case FLOW_STATS:
                vl = formatBytes(bytes);
                // default to "secondary highlighting" of link
                break;

            case PORT_STATS:
                vl = formatClippedBitRate(rate);

                // set color based on bits per second...
                if (vl.magnitude() == Magnitude.ONE ||
                        vl.magnitude() == Magnitude.KILO) {
                    m = PORT_TRAFFIC_GREEN;

                } else if (vl.magnitude() == Magnitude.MEGA) {
                    m = PORT_TRAFFIC_YELLOW;

                } else if (vl.magnitude() == Magnitude.GIGA) {
                    m = vl.clipped() ? PORT_TRAFFIC_RED : PORT_TRAFFIC_ORANGE;
                }
                break;

            case PORT_PACKET_STATS:
                vl = formatPacketRate(rate);

                // FIXME: Provisional color threshold parameters for packets
                // set color based on bits per second...
                if (rate < 10) {
                    m = PORT_TRAFFIC_GREEN;

                } else if (rate < 1000) {
                    m = PORT_TRAFFIC_YELLOW;

                } else if (rate < 100000) {
                    m = PORT_TRAFFIC_ORANGE;
                } else {
                    m = PORT_TRAFFIC_RED;
                }
                break;

            default:
                break;
        }

        LinkHighlight hlite = new LinkHighlight(linkId(), SECONDARY_HIGHLIGHT);
        if (vl != null) {
            hlite.setLabel(vl.toString());
        }
        if (m != null) {
            hlite.addMod(m);
        }

        return addCustomMods(hlite);
    }

    private LinkHighlight highlightForFlowCount() {
        Flavor flavor = flows > 0 ? PRIMARY_HIGHLIGHT : SECONDARY_HIGHLIGHT;
        LinkHighlight hlite = new LinkHighlight(linkId(), flavor)
                .setLabel(formatFlows(flows));

        return addCustomMods(hlite);
    }

    private LinkHighlight highlightForTagging() {
        LinkHighlight hlite = new LinkHighlight(linkId(), taggedFlavor)
                .setLabel(hasTraffic ? formatBytes(bytes).toString() : EMPTY);

        if (isOptical) {
            hlite.addMod(LinkHighlight.MOD_OPTICAL);
        }
        if (antMarch) {
            hlite.addMod(LinkHighlight.MOD_ANIMATED);
        }
        return addCustomMods(hlite);
    }

    private LinkHighlight addCustomMods(LinkHighlight hlite) {
        if (!mods.isEmpty()) {
            mods.forEach(hlite::addMod);
        }
        return hlite;
    }

    /**
     * Returns true if this link has been deemed to have enough traffic
     * to register on the topology view in the web UI.
     *
     * @return true if this link has displayable traffic
     */
    public boolean hasTraffic() {
        return hasTraffic;
    }

    /**
     * Designates type of traffic statistics to report on a highlighted link.
     */
    public enum StatsType {
        /**
         * Number of flows.
         */
        FLOW_COUNT,

        /**
         * Number of bytes.
         */
        FLOW_STATS,

        /**
         * Number of bits per second.
         */
        PORT_STATS,

        /**
         * Number of packets per second.
         */
        PORT_PACKET_STATS,

        /**
         * Custom tagged information.
         */
        TAGGED
    }
}
