| package net.floodlightcontroller.linkdiscovery.internal; |
| |
| import java.util.*; |
| |
| import org.openflow.util.HexString; |
| import org.slf4j.Logger; |
| import org.slf4j.LoggerFactory; |
| |
| import net.floodlightcontroller.linkdiscovery.LinkInfo; |
| import net.floodlightcontroller.routing.Link; |
| import net.floodlightcontroller.linkdiscovery.ILinkStorage; |
| |
| import org.apache.commons.configuration.BaseConfiguration; |
| import org.apache.commons.configuration.Configuration; |
| import com.thinkaurelius.titan.core.TitanException; |
| import com.thinkaurelius.titan.core.TitanFactory; |
| import com.thinkaurelius.titan.core.TitanGraph; |
| import com.tinkerpop.blueprints.Direction; |
| import com.tinkerpop.blueprints.TransactionalGraph.Conclusion; |
| import com.tinkerpop.blueprints.Vertex; |
| |
| public class LinkStorageImpl implements ILinkStorage { |
| public TitanGraph graph; |
| protected static Logger log = LoggerFactory.getLogger(LinkStorageImpl.class); |
| |
| @Override |
| public void update(Link link, DM_OPERATION op) { |
| update (link, (LinkInfo)null, op); |
| } |
| |
| @Override |
| public void update(List<Link> links, DM_OPERATION op) { |
| log.debug("LinkStorage:update(): {} {}", op, links); |
| |
| for (Link lt: links) { |
| update(lt, op); |
| } |
| } |
| |
| @Override |
| public void update(Link link, LinkInfo linkinfo, DM_OPERATION op) { |
| log.debug("LinkStorage:update(): {} {}", op, link); |
| |
| switch (op) { |
| case UPDATE: |
| case CREATE: |
| case INSERT: |
| addLink(link, linkinfo); |
| break; |
| case DELETE: |
| break; |
| } |
| } |
| |
| protected void addLink(Link lt, LinkInfo linkinfo) { |
| Vertex vswSrc, vswDst; |
| Vertex vportSrc = null, vportDst = null; |
| |
| log.info("addLink(): {} {} getSrc {}", new Object[]{lt, linkinfo, lt.getSrc()}); |
| |
| try { |
| // get source port vertex |
| String dpid = HexString.toHexString(lt.getSrc()); |
| short port = lt.getSrcPort(); |
| if ((vswSrc = graph.getVertices("dpid", dpid).iterator().next()) != null) { |
| log.debug("addLink(): sw exits {} {}", dpid, vswSrc); |
| if (vswSrc.query().direction(Direction.OUT).labels("on").has("number",port).vertices().iterator().hasNext()) { |
| vportSrc = vswSrc.query().direction(Direction.OUT).labels("on").has("number",port).vertices().iterator().next(); |
| log.debug("addLink(): port found {} {}", port, vportSrc); |
| } else { |
| log.error("addLink(): sw {} port {} not found", dpid, port); |
| } |
| } |
| |
| // get dest port vertex |
| dpid = HexString.toHexString(lt.getDst()); |
| port = lt.getDstPort(); |
| if ((vswDst = graph.getVertices("dpid",dpid).iterator().next()) != null) { |
| log.debug("addLink(): sw exits {} {}", dpid, vswDst); |
| if (vswDst.query().direction(Direction.OUT).labels("on").has("number",port).vertices().iterator().hasNext()) { |
| vportDst = vswDst.query().direction(Direction.OUT).labels("on").has("number",port).vertices().iterator().next(); |
| log.debug("addLink(): port found {} {}", port, vportDst); |
| } else { |
| log.error ("addLink(): sw {} port {} not found", dpid, port); |
| } |
| } |
| |
| if (vportSrc != null && vportDst != null) { |
| //TODO: If Edge already exists should we remove and add again? |
| if (vportSrc.query().direction(Direction.OUT).labels("link").vertices().iterator().hasNext() && |
| vportSrc.query().direction(Direction.OUT).labels("link").vertices().iterator().next().equals(vportDst)) { |
| //FIXME: Succeed silently for now |
| } else { |
| graph.addEdge(null, vportSrc, vportDst, "link"); |
| graph.stopTransaction(Conclusion.SUCCESS); |
| } |
| log.debug("addLink(): link added {} src {} dst {}", new Object[]{lt, vportSrc, vportDst}); |
| } else { |
| log.error("addLink(): failed {} src {} dst {}", new Object[]{lt, vportSrc, vportDst}); |
| graph.stopTransaction(Conclusion.FAILURE); |
| } |
| } catch (TitanException e) { |
| /* |
| * retry till we succeed? |
| */ |
| log.error("addLink(): {} failed", lt); |
| } |
| } |
| |
| @Override |
| public List<Link> getLinks(Long dpid, int port) { |
| // TODO Auto-generated method stub |
| return null; |
| } |
| |
| @Override |
| public void deleteLinks(Long dpid, int port) { |
| // TODO Auto-generated method stub |
| |
| } |
| |
| @Override |
| public void init(String conf) { |
| //TODO extract the DB location from conf |
| Configuration db = new BaseConfiguration(); |
| |
| // Local storage gets locked for single process |
| db.setProperty("storage.backend","cassandra"); |
| db.setProperty("storage.hostname","127.0.0.1"); |
| graph = TitanFactory.open(db); |
| |
| // FIXME: |
| Set<String> s = graph.getIndexedKeys(Vertex.class); |
| if (!s.contains("dpid")) { |
| graph.createKeyIndex("dpid", Vertex.class); |
| graph.stopTransaction(Conclusion.SUCCESS); |
| } |
| if (!s.contains("type")) { |
| graph.createKeyIndex("type", Vertex.class); |
| graph.stopTransaction(Conclusion.SUCCESS); |
| } |
| } |
| } |