package net.onrc.onos.ofcontroller.core.internal;

import java.util.ArrayList;
import java.util.List;

import net.floodlightcontroller.routing.Link;
import net.onrc.onos.graph.DBOperation;
import net.onrc.onos.ofcontroller.core.INetMapTopologyObjects.ISwitchObject;
import net.onrc.onos.ofcontroller.core.INetMapTopologyService.ITopoLinkService;

import org.openflow.util.HexString;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.tinkerpop.blueprints.Vertex;
import com.tinkerpop.gremlin.java.GremlinPipeline;
import net.onrc.onos.graph.GraphDBManager;
import com.tinkerpop.pipes.PipeFunction;
import com.tinkerpop.pipes.transform.PathPipe;

public class TopoLinkServiceImpl implements ITopoLinkService {
	
	protected DBOperation dbop;
	protected final static Logger log = LoggerFactory.getLogger(TopoLinkServiceImpl.class);

	@Override
	protected void finalize() {
		close();
	}

	@Override
	public void close() {
		dbop.close();
	}

	@Override
	public List<Link> getActiveLinks() {
		dbop = GraphDBManager.getDBOperation();
		Iterable<ISwitchObject> switches = dbop.getActiveSwitches();
		List<Link> links = new ArrayList<Link>(); 
		for (ISwitchObject sw : switches) {
			GremlinPipeline<Vertex, Link> pipe = new GremlinPipeline<Vertex, Link>();
			ExtractLink extractor = new ExtractLink();

			pipe.start(sw.asVertex());
			pipe.enablePath(true);
			pipe.out("on").out("link").in("on").path().step(extractor);

			while (pipe.hasNext() ) {
				Link l = pipe.next();
				links.add(l);
			}

		}
		dbop.commit();
		return links;
	}

	@Override
	public List<Link> getLinksOnSwitch(String dpid) {
		List<Link> links = new ArrayList<Link>(); 
		ISwitchObject sw = dbop.searchSwitch(dpid);
		GremlinPipeline<Vertex, Link> pipe = new GremlinPipeline<Vertex, Link>();
		ExtractLink extractor = new ExtractLink();

		pipe.start(sw.asVertex());
		pipe.enablePath(true);
		pipe.out("on").out("link").in("on").path().step(extractor);

		while (pipe.hasNext() ) {
			Link l = pipe.next();
			links.add(l);
		}
		return links;

	}

	private static class ExtractLink implements PipeFunction<PathPipe<Vertex>, Link> {
		@Override
		public Link compute(PathPipe<Vertex> pipe) {
			long s_dpid = 0;
			long d_dpid = 0;
			short s_port = 0;
			short d_port = 0;

			List<?> V = pipe.next();
			Vertex src_sw = (Vertex)V.get(0);
			Vertex dest_sw = (Vertex)V.get(3);
			Vertex src_port = (Vertex)V.get(1);
			Vertex dest_port = (Vertex)V.get(2);
			s_dpid = HexString.toLong((String) src_sw.getProperty("dpid"));
			d_dpid = HexString.toLong((String) dest_sw.getProperty("dpid"));
			s_port = (Short) src_port.getProperty("number");
			d_port = (Short) dest_port.getProperty("number");

			Link l = new Link(s_dpid,s_port,d_dpid,d_port);

			return l;
		}
	}
}
