ONOS-2186 - GUI Topo Overlay - (WIP)
- Moved TopoJson to core ui API, so it is accessible to external apps
- Added highlightsMessage() to TopoJson
- Pulled sendMessage() up to UiMessageHandler

Change-Id: Iacab5b69e3b2a6db98be8391274695247ba5526d
diff --git a/core/api/src/main/java/org/onosproject/ui/topo/TopoJson.java b/core/api/src/main/java/org/onosproject/ui/topo/TopoJson.java
new file mode 100644
index 0000000..a94068e
--- /dev/null
+++ b/core/api/src/main/java/org/onosproject/ui/topo/TopoJson.java
@@ -0,0 +1,160 @@
+/*
+ * Copyright 2015 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.topo;
+
+import com.fasterxml.jackson.databind.ObjectMapper;
+import com.fasterxml.jackson.databind.node.ArrayNode;
+import com.fasterxml.jackson.databind.node.ObjectNode;
+
+import static org.onosproject.ui.JsonUtils.envelope;
+
+/**
+ * JSON utilities for the Topology View.
+ */
+public final class TopoJson {
+    // package-private for unit test access
+    static final String SHOW_HIGHLIGHTS = "showHighlights";
+
+    static final String DEVICES = "devices";
+    static final String HOSTS = "hosts";
+    static final String LINKS = "links";
+    static final String SUBDUE = "subdue";
+
+    static final String ID = "id";
+    static final String LABEL = "label";
+    static final String CSS = "css";
+
+    static final String TITLE = "title";
+    static final String TYPE = "type";
+    static final String PROP_ORDER = "propOrder";
+    static final String PROPS = "props";
+    static final String BUTTONS = "buttons";
+
+
+    private static final ObjectMapper MAPPER = new ObjectMapper();
+
+    private static ObjectNode objectNode() {
+        return MAPPER.createObjectNode();
+    }
+
+    private static ArrayNode arrayNode() {
+        return MAPPER.createArrayNode();
+    }
+
+    // non-instantiable
+    private TopoJson() { }
+
+    /**
+     * Returns a formatted message ready to send to the topology view
+     * to render highlights.
+     *
+     * @param highlights highlights model to transform
+     * @return fully formatted "show highlights" message
+     */
+    public static ObjectNode highlightsMessage(Highlights highlights) {
+        return envelope(SHOW_HIGHLIGHTS, json(highlights));
+    }
+
+    /**
+     * Transforms the given highlights model into a JSON message payload.
+     *
+     * @param highlights the model to transform
+     * @return JSON payload
+     */
+    public static ObjectNode json(Highlights highlights) {
+        ObjectNode payload = objectNode();
+
+        ArrayNode devices = arrayNode();
+        ArrayNode hosts = arrayNode();
+        ArrayNode links = arrayNode();
+
+        payload.set(DEVICES, devices);
+        payload.set(HOSTS, hosts);
+        payload.set(LINKS, links);
+
+        highlights.devices().forEach(dh -> devices.add(json(dh)));
+        highlights.hosts().forEach(hh -> hosts.add(json(hh)));
+        highlights.links().forEach(lh -> links.add(json(lh)));
+
+        Highlights.Amount toSubdue = highlights.subdueLevel();
+        if (!toSubdue.equals(Highlights.Amount.ZERO)) {
+            payload.put(SUBDUE, toSubdue.toString());
+        }
+        return payload;
+    }
+
+    private static ObjectNode json(DeviceHighlight dh) {
+        ObjectNode n = objectNode()
+                .put(ID, dh.elementId());
+        if (dh.subdued()) {
+            n.put(SUBDUE, true);
+        }
+        return n;
+    }
+
+    private static ObjectNode json(HostHighlight hh) {
+        ObjectNode n = objectNode()
+                .put(ID, hh.elementId());
+        if (hh.subdued()) {
+            n.put(SUBDUE, true);
+        }
+        return n;
+    }
+
+    private static ObjectNode json(LinkHighlight lh) {
+        ObjectNode n = objectNode()
+                .put(ID, lh.elementId())
+                .put(LABEL, lh.label())
+                .put(CSS, lh.cssClasses());
+        if (lh.subdued()) {
+            n.put(SUBDUE, true);
+        }
+        return n;
+    }
+
+    /**
+     * Translates the given property panel into JSON, for returning
+     * to the client.
+     *
+     * @param pp the property panel model
+     * @return JSON payload
+     */
+    public static ObjectNode json(PropertyPanel pp) {
+        ObjectNode result = objectNode()
+                .put(TITLE, pp.title())
+                .put(TYPE, pp.typeId())
+                .put(ID, pp.id());
+
+        ObjectNode pnode = objectNode();
+        ArrayNode porder = arrayNode();
+        for (PropertyPanel.Prop p : pp.properties()) {
+            porder.add(p.key());
+            pnode.put(p.key(), p.value());
+        }
+        result.set(PROP_ORDER, porder);
+        result.set(PROPS, pnode);
+
+        ArrayNode buttons = arrayNode();
+        for (ButtonId b : pp.buttons()) {
+            buttons.add(b.id());
+        }
+        result.set(BUTTONS, buttons);
+        return result;
+    }
+
+}