Committed by
Gerrit Code Review
ONOS-3182 Starting on path visualization app.
Change-Id: Id9b074afb22599473b1849acc380fa189061e8bb
Showing
14 changed files
with
737 additions
and
0 deletions
apps/pathpainter/pom.xml
0 → 100644
| 1 | +<?xml version="1.0" encoding="UTF-8"?> | ||
| 2 | +<!-- | ||
| 3 | + ~ Copyright 2014 Open Networking Laboratory | ||
| 4 | + ~ | ||
| 5 | + ~ Licensed under the Apache License, Version 2.0 (the "License"); | ||
| 6 | + ~ you may not use this file except in compliance with the License. | ||
| 7 | + ~ You may obtain a copy of the License at | ||
| 8 | + ~ | ||
| 9 | + ~ http://www.apache.org/licenses/LICENSE-2.0 | ||
| 10 | + ~ | ||
| 11 | + ~ Unless required by applicable law or agreed to in writing, software | ||
| 12 | + ~ distributed under the License is distributed on an "AS IS" BASIS, | ||
| 13 | + ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
| 14 | + ~ See the License for the specific language governing permissions and | ||
| 15 | + ~ limitations under the License. | ||
| 16 | + --> | ||
| 17 | +<project xmlns="http://maven.apache.org/POM/4.0.0" | ||
| 18 | + xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" | ||
| 19 | + xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> | ||
| 20 | + <modelVersion>4.0.0</modelVersion> | ||
| 21 | + | ||
| 22 | + <parent> | ||
| 23 | + <groupId>org.onosproject</groupId> | ||
| 24 | + <artifactId>onos-apps</artifactId> | ||
| 25 | + <version>1.4.0-SNAPSHOT</version> | ||
| 26 | + <relativePath>../pom.xml</relativePath> | ||
| 27 | + </parent> | ||
| 28 | + | ||
| 29 | + <artifactId>onos-app-pp</artifactId> | ||
| 30 | + <packaging>bundle</packaging> | ||
| 31 | + | ||
| 32 | + <description>Path visualization application</description> | ||
| 33 | + | ||
| 34 | + <properties> | ||
| 35 | + <onos.app.name>org.onosproject.pathpainter</onos.app.name> | ||
| 36 | + </properties> | ||
| 37 | + | ||
| 38 | +</project> |
| 1 | +/* | ||
| 2 | + * Copyright 2014,2015 Open Networking Laboratory | ||
| 3 | + * | ||
| 4 | + * Licensed under the Apache License, Version 2.0 (the "License"); | ||
| 5 | + * you may not use this file except in compliance with the License. | ||
| 6 | + * You may obtain a copy of the License at | ||
| 7 | + * | ||
| 8 | + * http://www.apache.org/licenses/LICENSE-2.0 | ||
| 9 | + * | ||
| 10 | + * Unless required by applicable law or agreed to in writing, software | ||
| 11 | + * distributed under the License is distributed on an "AS IS" BASIS, | ||
| 12 | + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
| 13 | + * See the License for the specific language governing permissions and | ||
| 14 | + * limitations under the License. | ||
| 15 | + */ | ||
| 16 | +package org.onosproject.pathpainter; | ||
| 17 | + | ||
| 18 | +import org.onosproject.net.Link; | ||
| 19 | +import org.onosproject.net.LinkKey; | ||
| 20 | +import org.onosproject.ui.topo.BiLink; | ||
| 21 | +import org.onosproject.ui.topo.LinkHighlight; | ||
| 22 | +import org.onosproject.ui.topo.LinkHighlight.Flavor; | ||
| 23 | + | ||
| 24 | +import java.util.Set; | ||
| 25 | + | ||
| 26 | +/** | ||
| 27 | + * Bi-directional link capable of different hilights. | ||
| 28 | + */ | ||
| 29 | +public class PathLink extends BiLink { | ||
| 30 | + | ||
| 31 | + private boolean primary = false; | ||
| 32 | + private boolean secondary = false; | ||
| 33 | + | ||
| 34 | + public PathLink(LinkKey key, Link link) { | ||
| 35 | + super(key, link); | ||
| 36 | + } | ||
| 37 | + | ||
| 38 | + public void computeHilight(Set<Link> selectedLinks, Set<Link> allLinks) { | ||
| 39 | + primary = selectedLinks.contains(this.one()) || | ||
| 40 | + (two() != null && selectedLinks.contains(two())); | ||
| 41 | + secondary = allLinks.contains(this.one()) || | ||
| 42 | + (two() != null && allLinks.contains(two())); | ||
| 43 | + } | ||
| 44 | + | ||
| 45 | + @Override | ||
| 46 | + public LinkHighlight highlight(Enum<?> anEnum) { | ||
| 47 | + Flavor flavor = primary ? Flavor.PRIMARY_HIGHLIGHT : | ||
| 48 | + (secondary ? Flavor.SECONDARY_HIGHLIGHT : Flavor.NO_HIGHLIGHT); | ||
| 49 | + return new LinkHighlight(this.linkId(), flavor); | ||
| 50 | + } | ||
| 51 | +} |
| 1 | +/* | ||
| 2 | + * Copyright 2014,2015 Open Networking Laboratory | ||
| 3 | + * | ||
| 4 | + * Licensed under the Apache License, Version 2.0 (the "License"); | ||
| 5 | + * you may not use this file except in compliance with the License. | ||
| 6 | + * You may obtain a copy of the License at | ||
| 7 | + * | ||
| 8 | + * http://www.apache.org/licenses/LICENSE-2.0 | ||
| 9 | + * | ||
| 10 | + * Unless required by applicable law or agreed to in writing, software | ||
| 11 | + * distributed under the License is distributed on an "AS IS" BASIS, | ||
| 12 | + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
| 13 | + * See the License for the specific language governing permissions and | ||
| 14 | + * limitations under the License. | ||
| 15 | + */ | ||
| 16 | +package org.onosproject.pathpainter; | ||
| 17 | + | ||
| 18 | +import org.onosproject.net.Link; | ||
| 19 | +import org.onosproject.net.LinkKey; | ||
| 20 | +import org.onosproject.ui.topo.BiLinkMap; | ||
| 21 | + | ||
| 22 | +/** | ||
| 23 | + * Our concrete link map. | ||
| 24 | + */ | ||
| 25 | +public class PathLinkMap extends BiLinkMap<PathLink> { | ||
| 26 | + @Override | ||
| 27 | + protected PathLink create(LinkKey linkKey, Link link) { | ||
| 28 | + return new PathLink(linkKey, link); | ||
| 29 | + } | ||
| 30 | +} |
| 1 | +/* | ||
| 2 | + * Copyright 2014,2015 Open Networking Laboratory | ||
| 3 | + * | ||
| 4 | + * Licensed under the Apache License, Version 2.0 (the "License"); | ||
| 5 | + * you may not use this file except in compliance with the License. | ||
| 6 | + * You may obtain a copy of the License at | ||
| 7 | + * | ||
| 8 | + * http://www.apache.org/licenses/LICENSE-2.0 | ||
| 9 | + * | ||
| 10 | + * Unless required by applicable law or agreed to in writing, software | ||
| 11 | + * distributed under the License is distributed on an "AS IS" BASIS, | ||
| 12 | + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
| 13 | + * See the License for the specific language governing permissions and | ||
| 14 | + * limitations under the License. | ||
| 15 | + */ | ||
| 16 | +package org.onosproject.pathpainter; | ||
| 17 | + | ||
| 18 | +import com.google.common.collect.ImmutableList; | ||
| 19 | +import org.apache.felix.scr.annotations.Activate; | ||
| 20 | +import org.apache.felix.scr.annotations.Component; | ||
| 21 | +import org.apache.felix.scr.annotations.Deactivate; | ||
| 22 | +import org.apache.felix.scr.annotations.Reference; | ||
| 23 | +import org.apache.felix.scr.annotations.ReferenceCardinality; | ||
| 24 | +import org.onosproject.ui.UiExtension; | ||
| 25 | +import org.onosproject.ui.UiExtensionService; | ||
| 26 | +import org.onosproject.ui.UiMessageHandlerFactory; | ||
| 27 | +import org.onosproject.ui.UiTopoOverlayFactory; | ||
| 28 | +import org.onosproject.ui.UiView; | ||
| 29 | +import org.onosproject.ui.UiViewHidden; | ||
| 30 | +import org.slf4j.Logger; | ||
| 31 | +import org.slf4j.LoggerFactory; | ||
| 32 | + | ||
| 33 | +import java.util.List; | ||
| 34 | + | ||
| 35 | +/** | ||
| 36 | + * Skeletal ONOS UI Topology-Overlay application component. | ||
| 37 | + */ | ||
| 38 | +@Component(immediate = true) | ||
| 39 | +public class PathPainter { | ||
| 40 | + | ||
| 41 | + private static final ClassLoader CL = PathPainter.class.getClassLoader(); | ||
| 42 | + private static final String VIEW_ID = "ppTopov"; | ||
| 43 | + | ||
| 44 | + private final Logger log = LoggerFactory.getLogger(getClass()); | ||
| 45 | + | ||
| 46 | + @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY) | ||
| 47 | + protected UiExtensionService uiExtensionService; | ||
| 48 | + | ||
| 49 | + // List of application views | ||
| 50 | + private final List<UiView> uiViews = ImmutableList.of( | ||
| 51 | + new UiViewHidden(VIEW_ID) | ||
| 52 | + ); | ||
| 53 | + | ||
| 54 | + // Factory for UI message handlers | ||
| 55 | + private final UiMessageHandlerFactory messageHandlerFactory = | ||
| 56 | + () -> ImmutableList.of( | ||
| 57 | + new PathPainterTopovMessageHandler() | ||
| 58 | + ); | ||
| 59 | + | ||
| 60 | + // Factory for UI topology overlays | ||
| 61 | + private final UiTopoOverlayFactory topoOverlayFactory = | ||
| 62 | + () -> ImmutableList.of( | ||
| 63 | + new PathPainterTopovOverlay() | ||
| 64 | + ); | ||
| 65 | + | ||
| 66 | + // Application UI extension | ||
| 67 | + protected UiExtension extension = | ||
| 68 | + new UiExtension.Builder(CL, uiViews) | ||
| 69 | + .resourcePath(VIEW_ID) | ||
| 70 | + .messageHandlerFactory(messageHandlerFactory) | ||
| 71 | + .topoOverlayFactory(topoOverlayFactory) | ||
| 72 | + .build(); | ||
| 73 | + | ||
| 74 | + @Activate | ||
| 75 | + protected void activate() { | ||
| 76 | + uiExtensionService.register(extension); | ||
| 77 | + log.info("Started"); | ||
| 78 | + } | ||
| 79 | + | ||
| 80 | + @Deactivate | ||
| 81 | + protected void deactivate() { | ||
| 82 | + uiExtensionService.unregister(extension); | ||
| 83 | + log.info("Stopped"); | ||
| 84 | + } | ||
| 85 | + | ||
| 86 | +} |
apps/pathpainter/src/main/java/org/onosproject/pathpainter/PathPainterTopovMessageHandler.java
0 → 100644
| 1 | +/* | ||
| 2 | + * Copyright 2014,2015 Open Networking Laboratory | ||
| 3 | + * | ||
| 4 | + * Licensed under the Apache License, Version 2.0 (the "License"); | ||
| 5 | + * you may not use this file except in compliance with the License. | ||
| 6 | + * You may obtain a copy of the License at | ||
| 7 | + * | ||
| 8 | + * http://www.apache.org/licenses/LICENSE-2.0 | ||
| 9 | + * | ||
| 10 | + * Unless required by applicable law or agreed to in writing, software | ||
| 11 | + * distributed under the License is distributed on an "AS IS" BASIS, | ||
| 12 | + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
| 13 | + * See the License for the specific language governing permissions and | ||
| 14 | + * limitations under the License. | ||
| 15 | + */ | ||
| 16 | +package org.onosproject.pathpainter; | ||
| 17 | + | ||
| 18 | +import com.fasterxml.jackson.databind.node.ObjectNode; | ||
| 19 | +import com.google.common.collect.ImmutableList; | ||
| 20 | +import com.google.common.collect.ImmutableSet; | ||
| 21 | +import org.onlab.osgi.ServiceDirectory; | ||
| 22 | +import org.onosproject.net.DeviceId; | ||
| 23 | +import org.onosproject.net.ElementId; | ||
| 24 | +import org.onosproject.net.HostId; | ||
| 25 | +import org.onosproject.net.Link; | ||
| 26 | +import org.onosproject.net.Path; | ||
| 27 | +import org.onosproject.net.topology.PathService; | ||
| 28 | +import org.onosproject.ui.RequestHandler; | ||
| 29 | +import org.onosproject.ui.UiConnection; | ||
| 30 | +import org.onosproject.ui.UiMessageHandler; | ||
| 31 | +import org.onosproject.ui.topo.Highlights; | ||
| 32 | +import org.onosproject.ui.topo.TopoJson; | ||
| 33 | +import org.slf4j.Logger; | ||
| 34 | +import org.slf4j.LoggerFactory; | ||
| 35 | + | ||
| 36 | +import java.util.Collection; | ||
| 37 | +import java.util.List; | ||
| 38 | +import java.util.Set; | ||
| 39 | + | ||
| 40 | +/** | ||
| 41 | + * Skeletal ONOS UI Topology-Overlay message handler. | ||
| 42 | + */ | ||
| 43 | +public class PathPainterTopovMessageHandler extends UiMessageHandler { | ||
| 44 | + | ||
| 45 | + private static final String PAINTER_SET_SRC = "ppTopovSetSrc"; | ||
| 46 | + private static final String PAINTER_SET_DST = "ppTopovSetDst"; | ||
| 47 | + private static final String PAINTER_SWAP_SRC_DST = "ppTopovSwapSrcDst"; | ||
| 48 | + private static final String PAINTER_SET_MODE = "ppTopovSetMode"; | ||
| 49 | + | ||
| 50 | + private static final String PAINTER_NEXT_PATH = "ppTopovNextPath"; | ||
| 51 | + private static final String PAINTER_PREV_PATH = "ppTopovPrevPath"; | ||
| 52 | + | ||
| 53 | + private static final String ID = "id"; | ||
| 54 | + private static final String MODE = "mode"; | ||
| 55 | + | ||
| 56 | + private Set<Link> allPathLinks; | ||
| 57 | + | ||
| 58 | + private enum Mode { | ||
| 59 | + SHORTEST, DISJOINT, SRLG | ||
| 60 | + } | ||
| 61 | + | ||
| 62 | + private final Logger log = LoggerFactory.getLogger(getClass()); | ||
| 63 | + | ||
| 64 | + private PathService pathService; | ||
| 65 | + | ||
| 66 | + private Mode currentMode = Mode.SHORTEST; | ||
| 67 | + private ElementId src, dst; | ||
| 68 | + private Mode mode = Mode.SHORTEST; | ||
| 69 | + private List<Path> paths; | ||
| 70 | + private int pathIndex; | ||
| 71 | + | ||
| 72 | + | ||
| 73 | + // ===============-=-=-=-=-=-======================-=-=-=-=-=-=-================================ | ||
| 74 | + | ||
| 75 | + | ||
| 76 | + @Override | ||
| 77 | + public void init(UiConnection connection, ServiceDirectory directory) { | ||
| 78 | + super.init(connection, directory); | ||
| 79 | + pathService = directory.get(PathService.class); | ||
| 80 | + } | ||
| 81 | + | ||
| 82 | + @Override | ||
| 83 | + protected Collection<RequestHandler> createRequestHandlers() { | ||
| 84 | + return ImmutableSet.of( | ||
| 85 | + new SetSrcHandler(), | ||
| 86 | + new SetDstHandler(), | ||
| 87 | + new NextPathHandler(), | ||
| 88 | + new PrevPathHandler() | ||
| 89 | + ); | ||
| 90 | + } | ||
| 91 | + | ||
| 92 | + // === ------------------------- | ||
| 93 | + // === Handler classes | ||
| 94 | + | ||
| 95 | + private final class SetSrcHandler extends RequestHandler { | ||
| 96 | + public SetSrcHandler() { | ||
| 97 | + super(PAINTER_SET_SRC); | ||
| 98 | + } | ||
| 99 | + | ||
| 100 | + @Override | ||
| 101 | + public void process(long sid, ObjectNode payload) { | ||
| 102 | + String id = string(payload, ID); | ||
| 103 | + src = elementId(id); | ||
| 104 | + if (src.equals(dst)) { | ||
| 105 | + dst = null; | ||
| 106 | + } | ||
| 107 | + findAndSendPaths(); | ||
| 108 | + } | ||
| 109 | + } | ||
| 110 | + | ||
| 111 | + private final class SetDstHandler extends RequestHandler { | ||
| 112 | + public SetDstHandler() { | ||
| 113 | + super(PAINTER_SET_DST); | ||
| 114 | + } | ||
| 115 | + | ||
| 116 | + @Override | ||
| 117 | + public void process(long sid, ObjectNode payload) { | ||
| 118 | + String id = string(payload, ID); | ||
| 119 | + dst = elementId(id); | ||
| 120 | + if (src.equals(dst)) { | ||
| 121 | + src = null; | ||
| 122 | + } | ||
| 123 | + findAndSendPaths(); | ||
| 124 | + } | ||
| 125 | + } | ||
| 126 | + | ||
| 127 | + private final class NextPathHandler extends RequestHandler { | ||
| 128 | + public NextPathHandler() { | ||
| 129 | + super(PAINTER_NEXT_PATH); | ||
| 130 | + } | ||
| 131 | + | ||
| 132 | + @Override | ||
| 133 | + public void process(long sid, ObjectNode payload) { | ||
| 134 | + pathIndex = (pathIndex >= paths.size() - 1 ? 0 : pathIndex + 1); | ||
| 135 | + hilightAndSendPaths(); | ||
| 136 | + } | ||
| 137 | + } | ||
| 138 | + | ||
| 139 | + private final class PrevPathHandler extends RequestHandler { | ||
| 140 | + public PrevPathHandler() { | ||
| 141 | + super(PAINTER_PREV_PATH); | ||
| 142 | + } | ||
| 143 | + | ||
| 144 | + @Override | ||
| 145 | + public void process(long sid, ObjectNode payload) { | ||
| 146 | + pathIndex = (pathIndex <= 0 ? paths.size() - 1 : pathIndex - 1); | ||
| 147 | + hilightAndSendPaths(); | ||
| 148 | + } | ||
| 149 | + } | ||
| 150 | + | ||
| 151 | + // === ------------ | ||
| 152 | + | ||
| 153 | + private ElementId elementId(String id) { | ||
| 154 | + try { | ||
| 155 | + return DeviceId.deviceId(id); | ||
| 156 | + } catch (IllegalArgumentException e) { | ||
| 157 | + return HostId.hostId(id); | ||
| 158 | + } | ||
| 159 | + } | ||
| 160 | + | ||
| 161 | + private void findAndSendPaths() { | ||
| 162 | + log.info("src={}; dst={}; mode={}", src, dst, mode); | ||
| 163 | + if (src != null && dst != null) { | ||
| 164 | + paths = ImmutableList.copyOf(pathService.getPaths(src, dst)); | ||
| 165 | + pathIndex = 0; | ||
| 166 | + | ||
| 167 | + ImmutableSet.Builder<Link> builder = ImmutableSet.builder(); | ||
| 168 | + paths.forEach(path -> path.links().forEach(builder::add)); | ||
| 169 | + allPathLinks = builder.build(); | ||
| 170 | + } else { | ||
| 171 | + paths = ImmutableList.of(); | ||
| 172 | + allPathLinks = ImmutableSet.of(); | ||
| 173 | + } | ||
| 174 | + hilightAndSendPaths(); | ||
| 175 | + } | ||
| 176 | + | ||
| 177 | + private void hilightAndSendPaths() { | ||
| 178 | + PathLinkMap linkMap = new PathLinkMap(); | ||
| 179 | + allPathLinks.forEach(linkMap::add); | ||
| 180 | + | ||
| 181 | + // Prepare two working sets; one containing selected path links and | ||
| 182 | + // the other containing all paths links. | ||
| 183 | + Set<Link> selectedPathLinks = paths.isEmpty() ? | ||
| 184 | + ImmutableSet.of() : ImmutableSet.copyOf(paths.get(pathIndex).links()); | ||
| 185 | + | ||
| 186 | + Highlights highlights = new Highlights(); | ||
| 187 | + for (PathLink plink : linkMap.biLinks()) { | ||
| 188 | + plink.computeHilight(selectedPathLinks, allPathLinks); | ||
| 189 | + highlights.add(plink.highlight(null)); | ||
| 190 | + } | ||
| 191 | + | ||
| 192 | + sendMessage(TopoJson.highlightsMessage(highlights)); | ||
| 193 | + } | ||
| 194 | + | ||
| 195 | + /* | ||
| 196 | + private void addDeviceBadge(Highlights h, DeviceId devId, int n) { | ||
| 197 | + DeviceHighlight dh = new DeviceHighlight(devId.toString()); | ||
| 198 | + dh.setBadge(createBadge(n)); | ||
| 199 | + h.add(dh); | ||
| 200 | + } | ||
| 201 | + | ||
| 202 | + private NodeBadge createBadge(int n) { | ||
| 203 | + Status status = n > 3 ? Status.ERROR : Status.WARN; | ||
| 204 | + String noun = n > 3 ? "(critical)" : "(problematic)"; | ||
| 205 | + String msg = "Egress links: " + n + " " + noun; | ||
| 206 | + return NodeBadge.number(status, n, msg); | ||
| 207 | + } | ||
| 208 | + */ | ||
| 209 | + | ||
| 210 | +} | ||
| ... | \ No newline at end of file | ... | \ No newline at end of file |
| 1 | +/* | ||
| 2 | + * Copyright 2014,2015 Open Networking Laboratory | ||
| 3 | + * | ||
| 4 | + * Licensed under the Apache License, Version 2.0 (the "License"); | ||
| 5 | + * you may not use this file except in compliance with the License. | ||
| 6 | + * You may obtain a copy of the License at | ||
| 7 | + * | ||
| 8 | + * http://www.apache.org/licenses/LICENSE-2.0 | ||
| 9 | + * | ||
| 10 | + * Unless required by applicable law or agreed to in writing, software | ||
| 11 | + * distributed under the License is distributed on an "AS IS" BASIS, | ||
| 12 | + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
| 13 | + * See the License for the specific language governing permissions and | ||
| 14 | + * limitations under the License. | ||
| 15 | + */ | ||
| 16 | +package org.onosproject.pathpainter; | ||
| 17 | + | ||
| 18 | +import org.onosproject.net.DeviceId; | ||
| 19 | +import org.onosproject.net.HostId; | ||
| 20 | +import org.onosproject.ui.UiTopoOverlay; | ||
| 21 | +import org.onosproject.ui.topo.ButtonId; | ||
| 22 | +import org.onosproject.ui.topo.PropertyPanel; | ||
| 23 | + | ||
| 24 | +/** | ||
| 25 | + * Our topology overlay. | ||
| 26 | + */ | ||
| 27 | +public class PathPainterTopovOverlay extends UiTopoOverlay { | ||
| 28 | + | ||
| 29 | + // NOTE: this must match the ID defined in ppTopovOverlay.js | ||
| 30 | + private static final String OVERLAY_ID = "pp-overlay"; | ||
| 31 | + | ||
| 32 | + private static final ButtonId SRC_BUTTON = new ButtonId("src"); | ||
| 33 | + private static final ButtonId DST_BUTTON = new ButtonId("dst"); | ||
| 34 | + | ||
| 35 | + public PathPainterTopovOverlay() { | ||
| 36 | + super(OVERLAY_ID); | ||
| 37 | + } | ||
| 38 | + | ||
| 39 | + @Override | ||
| 40 | + public void modifyDeviceDetails(PropertyPanel pp, DeviceId deviceId) { | ||
| 41 | + pp.addButton(SRC_BUTTON).addButton(DST_BUTTON); | ||
| 42 | + } | ||
| 43 | + | ||
| 44 | + @Override | ||
| 45 | + public void modifyHostDetails(PropertyPanel pp, HostId hostId) { | ||
| 46 | + pp.addButton(SRC_BUTTON).addButton(DST_BUTTON); | ||
| 47 | + } | ||
| 48 | + | ||
| 49 | + | ||
| 50 | +} |
| 1 | +/* | ||
| 2 | + * Copyright 2014-2015 Open Networking Laboratory | ||
| 3 | + * | ||
| 4 | + * Licensed under the Apache License, Version 2.0 (the "License"); | ||
| 5 | + * you may not use this file except in compliance with the License. | ||
| 6 | + * You may obtain a copy of the License at | ||
| 7 | + * | ||
| 8 | + * http://www.apache.org/licenses/LICENSE-2.0 | ||
| 9 | + * | ||
| 10 | + * Unless required by applicable law or agreed to in writing, software | ||
| 11 | + * distributed under the License is distributed on an "AS IS" BASIS, | ||
| 12 | + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
| 13 | + * See the License for the specific language governing permissions and | ||
| 14 | + * limitations under the License. | ||
| 15 | + */ | ||
| 16 | + | ||
| 17 | +/** | ||
| 18 | + * Path visualization GUI topology view overlay. | ||
| 19 | + */ | ||
| 20 | +package org.onosproject.pathpainter; | ||
| ... | \ No newline at end of file | ... | \ No newline at end of file |
| 1 | +/* | ||
| 2 | + * Copyright 2015 Open Networking Laboratory | ||
| 3 | + * | ||
| 4 | + * Licensed under the Apache License, Version 2.0 (the "License"); | ||
| 5 | + * you may not use this file except in compliance with the License. | ||
| 6 | + * You may obtain a copy of the License at | ||
| 7 | + * | ||
| 8 | + * http://www.apache.org/licenses/LICENSE-2.0 | ||
| 9 | + * | ||
| 10 | + * Unless required by applicable law or agreed to in writing, software | ||
| 11 | + * distributed under the License is distributed on an "AS IS" BASIS, | ||
| 12 | + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
| 13 | + * See the License for the specific language governing permissions and | ||
| 14 | + * limitations under the License. | ||
| 15 | + */ | ||
| 16 | + | ||
| 17 | +/* | ||
| 18 | + Sample Demo module. This contains the "business logic" for the topology | ||
| 19 | + overlay that we are implementing. | ||
| 20 | + */ | ||
| 21 | + | ||
| 22 | +(function () { | ||
| 23 | + 'use strict'; | ||
| 24 | + | ||
| 25 | + // injected refs | ||
| 26 | + var $log, fs, flash, wss; | ||
| 27 | + | ||
| 28 | + // constants | ||
| 29 | + var srcMessage = 'ppTopovSetSrc', | ||
| 30 | + dstMessage = 'ppTopovSetDst', | ||
| 31 | + modeMessage = 'ppTopovSetMode', | ||
| 32 | + nextPathMessage = 'ppTopovNextPath', | ||
| 33 | + prevPathMessage = 'ppTopovPrevPath'; | ||
| 34 | + | ||
| 35 | + // internal state | ||
| 36 | + var currentMode = null; | ||
| 37 | + | ||
| 38 | + | ||
| 39 | + // === --------------------------- | ||
| 40 | + // === Helper functions | ||
| 41 | + | ||
| 42 | + | ||
| 43 | + // === --------------------------- | ||
| 44 | + // === Main API functions | ||
| 45 | + | ||
| 46 | + | ||
| 47 | + function setSrc(node) { | ||
| 48 | + wss.sendEvent(srcMessage, { | ||
| 49 | + id: node.id | ||
| 50 | + }); | ||
| 51 | + flash.flash('Source node: ' + node.id); | ||
| 52 | + } | ||
| 53 | + | ||
| 54 | + function setDst(node) { | ||
| 55 | + wss.sendEvent(dstMessage, { | ||
| 56 | + id: node.id | ||
| 57 | + }); | ||
| 58 | + flash.flash('Destination node: ' + node.id); | ||
| 59 | + } | ||
| 60 | + | ||
| 61 | + function nextPath(node) { | ||
| 62 | + wss.sendEvent(nextPathMessage); | ||
| 63 | + } | ||
| 64 | + | ||
| 65 | + function prevPath(node) { | ||
| 66 | + wss.sendEvent(prevPathMessage); | ||
| 67 | + } | ||
| 68 | + | ||
| 69 | + | ||
| 70 | + function setMode(mode) { | ||
| 71 | + if (currentMode === mode) { | ||
| 72 | + $log.debug('(in mode', mode, 'already)'); | ||
| 73 | + } else { | ||
| 74 | + currentMode = mode; | ||
| 75 | + wss.sendEvent(modeMessage, { | ||
| 76 | + mode: mode | ||
| 77 | + }); | ||
| 78 | + flash.flash('Path mode: ' + mode); | ||
| 79 | + } | ||
| 80 | + } | ||
| 81 | + | ||
| 82 | + // === --------------------------- | ||
| 83 | + // === Module Factory Definition | ||
| 84 | + | ||
| 85 | + angular.module('ovPpTopov', []) | ||
| 86 | + .factory('PathPainterTopovService', | ||
| 87 | + ['$log', 'FnService', 'FlashService', 'WebSocketService', | ||
| 88 | + | ||
| 89 | + function (_$log_, _fs_, _flash_, _wss_) { | ||
| 90 | + $log = _$log_; | ||
| 91 | + fs = _fs_; | ||
| 92 | + flash = _flash_; | ||
| 93 | + wss = _wss_; | ||
| 94 | + | ||
| 95 | + return { | ||
| 96 | + setSrc: setSrc, | ||
| 97 | + setDst: setDst, | ||
| 98 | + setMode: setMode, | ||
| 99 | + nextPath: nextPath, | ||
| 100 | + prevPath: prevPath | ||
| 101 | + }; | ||
| 102 | + }]); | ||
| 103 | +}()); |
| 1 | +// path painter topology overlay - client side | ||
| 2 | +// | ||
| 3 | +// This is the glue that binds our business logic (in ppTopovDemo.js) | ||
| 4 | +// to the overlay framework. | ||
| 5 | + | ||
| 6 | +(function () { | ||
| 7 | + 'use strict'; | ||
| 8 | + | ||
| 9 | + // injected refs | ||
| 10 | + var $log, tov, pps; | ||
| 11 | + | ||
| 12 | + // internal state should be kept in the service module (not here) | ||
| 13 | + var selection; | ||
| 14 | + | ||
| 15 | + // our overlay definition | ||
| 16 | + var overlay = { | ||
| 17 | + // NOTE: this must match the ID defined in AppUiTopovOverlay | ||
| 18 | + overlayId: 'pp-overlay', | ||
| 19 | + // FIXME: new icon for the overlay | ||
| 20 | + glyphId: '*star4', | ||
| 21 | + tooltip: 'Path Painter Topo Overlay', | ||
| 22 | + | ||
| 23 | + // These glyphs get installed using the overlayId as a prefix. | ||
| 24 | + // e.g. 'star4' is installed as 'meowster-overlay-star4' | ||
| 25 | + // They can be referenced (from this overlay) as '*star4' | ||
| 26 | + // That is, the '*' prefix stands in for 'meowster-overlay-' | ||
| 27 | + glyphs: { | ||
| 28 | + star4: { | ||
| 29 | + vb: '0 0 8 8', | ||
| 30 | + d: 'M1,4l2,-1l1,-2l1,2l2,1l-2,1l-1,2l-1,-2z' | ||
| 31 | + }, | ||
| 32 | + banner: { | ||
| 33 | + vb: '0 0 6 6', | ||
| 34 | + d: 'M1,1v4l2,-2l2,2v-4z' | ||
| 35 | + } | ||
| 36 | + }, | ||
| 37 | + | ||
| 38 | + activate: function () { | ||
| 39 | + $log.debug("Path painter topology overlay ACTIVATED"); | ||
| 40 | + }, | ||
| 41 | + deactivate: function () { | ||
| 42 | + $log.debug("Path painter topology overlay DEACTIVATED"); | ||
| 43 | + }, | ||
| 44 | + | ||
| 45 | + // detail panel button definitions | ||
| 46 | + // FIXME: new icons for src/dst | ||
| 47 | + buttons: { | ||
| 48 | + src: { | ||
| 49 | + gid: 'triangleUp', | ||
| 50 | + tt: 'Set source node', | ||
| 51 | + cb: function (data) { | ||
| 52 | + $log.debug('Set src action invoked with data:', data); | ||
| 53 | + pps.setSrc(selection); | ||
| 54 | + } | ||
| 55 | + }, | ||
| 56 | + dst: { | ||
| 57 | + gid: 'triangleDown', | ||
| 58 | + tt: 'Set destination node', | ||
| 59 | + cb: function (data) { | ||
| 60 | + $log.debug('Set dst action invoked with data:', data); | ||
| 61 | + pps.setDst(selection); | ||
| 62 | + } | ||
| 63 | + } | ||
| 64 | + }, | ||
| 65 | + | ||
| 66 | + // Key bindings for traffic overlay buttons | ||
| 67 | + // NOTE: fully qual. button ID is derived from overlay-id and key-name | ||
| 68 | + // FIXME: use into [ and ] instead of 1 and 2 | ||
| 69 | + // FIXME: new icons for src/dst | ||
| 70 | + // TODO: add keys for shortest paths & disjoint paths modes | ||
| 71 | + // TODO: add key for src/dst swap; with its own icon | ||
| 72 | + keyBindings: { | ||
| 73 | + 1: { | ||
| 74 | + cb: function () { pps.setSrc(selection); }, | ||
| 75 | + tt: 'Set source node', | ||
| 76 | + gid: 'triangleUp' | ||
| 77 | + }, | ||
| 78 | + 2: { | ||
| 79 | + cb: function () { pps.setDst(selection); }, | ||
| 80 | + tt: 'Set destination node', | ||
| 81 | + gid: 'triangleDown' | ||
| 82 | + }, | ||
| 83 | + leftArrow: { | ||
| 84 | + cb: function () { pps.prevPath(); }, | ||
| 85 | + tt: 'Highlight previous path', | ||
| 86 | + gid: 'prevIntent' | ||
| 87 | + }, | ||
| 88 | + rightArrow: { | ||
| 89 | + cb: function () { pps.nextPath(); }, | ||
| 90 | + tt: 'Highlight next path', | ||
| 91 | + gid: 'nextIntent' | ||
| 92 | + }, | ||
| 93 | + | ||
| 94 | + _keyOrder: [ | ||
| 95 | + '1', '2', 'leftArrow', 'rightArrow' | ||
| 96 | + ] | ||
| 97 | + }, | ||
| 98 | + | ||
| 99 | + hooks: { | ||
| 100 | + // hook for handling escape key | ||
| 101 | + // Must return true to consume ESC, false otherwise. | ||
| 102 | + escape: function () { | ||
| 103 | + selectionCallback(); | ||
| 104 | + pps.setSrc(); | ||
| 105 | + pps.setDst(); | ||
| 106 | + }, | ||
| 107 | + | ||
| 108 | + // hooks for when the selection changes... | ||
| 109 | + empty: function () { | ||
| 110 | + selectionCallback(); | ||
| 111 | + }, | ||
| 112 | + single: function (data) { | ||
| 113 | + selectionCallback(data); | ||
| 114 | + } | ||
| 115 | + } | ||
| 116 | + }; | ||
| 117 | + | ||
| 118 | + | ||
| 119 | + function buttonCallback(x) { | ||
| 120 | + $log.debug('Toolbar-button callback', x); | ||
| 121 | + } | ||
| 122 | + | ||
| 123 | + function selectionCallback(d) { | ||
| 124 | + $log.debug('Selection callback', d); | ||
| 125 | + selection = d; | ||
| 126 | + } | ||
| 127 | + | ||
| 128 | + // invoke code to register with the overlay service | ||
| 129 | + angular.module('ovPpTopov') | ||
| 130 | + .run(['$log', 'TopoOverlayService', 'PathPainterTopovService', | ||
| 131 | + | ||
| 132 | + function (_$log_, _tov_, _pps_) { | ||
| 133 | + $log = _$log_; | ||
| 134 | + tov = _tov_; | ||
| 135 | + pps = _pps_; | ||
| 136 | + tov.register(overlay); | ||
| 137 | + }]); | ||
| 138 | + | ||
| 139 | +}()); |
| 1 | +<link rel="stylesheet" href="app/view/ppTopov/ppTopov.css"> | ||
| ... | \ No newline at end of file | ... | \ No newline at end of file |
| ... | @@ -59,6 +59,7 @@ | ... | @@ -59,6 +59,7 @@ |
| 59 | <module>pim</module> | 59 | <module>pim</module> |
| 60 | <module>mlb</module> | 60 | <module>mlb</module> |
| 61 | <module>openstackswitching</module> | 61 | <module>openstackswitching</module> |
| 62 | + <module>pathpainter</module> | ||
| 62 | </modules> | 63 | </modules> |
| 63 | 64 | ||
| 64 | <properties> | 65 | <properties> | ... | ... |
-
Please register or login to post a comment