diff --git a/src/main/java/net/floodlightcontroller/linkdiscovery/internal/LinkStorageImpl.java b/src/main/java/net/floodlightcontroller/linkdiscovery/internal/LinkStorageImpl.java
index f8f50a3..ac76def 100644
--- a/src/main/java/net/floodlightcontroller/linkdiscovery/internal/LinkStorageImpl.java
+++ b/src/main/java/net/floodlightcontroller/linkdiscovery/internal/LinkStorageImpl.java
@@ -28,11 +28,21 @@
 	protected static Logger log = LoggerFactory.getLogger(LinkStorageImpl.class);
 	protected GraphDBOperation dbop;
 
+	/**
+	 * Update a record in the LinkStorage in a way provided by op.
+	 * @param link Record of a link to be updated.
+	 * @param op Operation to be done.
+	 */
 	@Override
 	public void update(Link link, DM_OPERATION op) {
 		update(link, (LinkInfo)null, op);
 	}
 
+	/**
+	 * Update multiple records in the LinkStorage in a way provided by op.
+	 * @param links List of records to be updated.
+	 * @param op Operation to be done.
+	 */
 	@Override
 	public void update(List<Link> links, DM_OPERATION op) {
 		for (Link lt: links) {
@@ -40,6 +50,12 @@
 		}
 	}
 
+	/**
+	 * Update a record of link with meta-information in the LinkStorage in a way provided by op.
+	 * @param link Record of a link to update.
+	 * @param linkinfo Meta-information of a link to be updated.
+	 * @param op Operation to be done.
+	 */
 	@Override
 	public void update(Link link, LinkInfo linkinfo, DM_OPERATION op) {
 		switch (op) {
@@ -54,6 +70,12 @@
 		}
 	}
 	
+	/**
+	 * Perform INSERT/CREATE/UPDATE operation to update the LinkStorage.
+	 * @param lt Record of a link to be updated.
+	 * @param linkinfo Meta-information of a link to be updated.
+	 * @param op Operation to be done. (only INSERT/CREATE/UPDATE is acceptable)
+	 */
 	public void updateLink(Link lt, LinkInfo linkinfo, DM_OPERATION op) {
 		IPortObject vportSrc = null, vportDst = null;
 	
@@ -71,7 +93,6 @@
             vportDst = dbop.searchPort(dpid, port);
                         
             if (vportSrc != null && vportDst != null) {
-         	       	
             	// check if the link exists
             	
             	Iterable<IPortObject> currPorts = vportSrc.getLinkedPorts();
@@ -79,7 +100,7 @@
             	for (IPortObject V : currPorts) {
             		currLinks.add(V);
             	}
-            	
+
             	if (currLinks.contains(vportDst)) {
             		// TODO: update linkinfo
             		if (op.equals(DM_OPERATION.INSERT) || op.equals(DM_OPERATION.CREATE)) {
@@ -105,6 +126,10 @@
         }
 	}
 	
+	/**
+	 * Delete multiple records in the LinkStorage.
+	 * @param links List of records to be deleted.
+	 */
 	@Override
 	public void deleteLinks(List<Link> links) {
 
@@ -113,7 +138,10 @@
 		}
 	}
 	
-
+	/**
+	 * Delete a record in the LinkStorage.
+	 * @param link Record to be deleted.
+	 */
 	@Override
 	public void deleteLink(Link lt) {
 		IPortObject vportSrc = null, vportDst = null;
@@ -163,43 +191,64 @@
         }
 	}
 
+	/**
+	 * Get list of all links connected to the port specified by given DPID and port number.
+	 * @param dpid DPID of desired port.
+	 * @param port Port number of desired port.
+	 * @return List of links. Empty list if no port was found.
+	 */
 	// TODO: Fix me
 	@Override
 	public List<Link> getLinks(Long dpid, short port) {
-		IPortObject vportSrc, vportDst;
     	List<Link> links = null;
-    	Link lt;
-    	
-		vportSrc = dbop.searchPort(HexString.toHexString(dpid), port);
-		if (vportSrc != null) {
-			
-     		for (Edge e : vportSrc.asVertex().getEdges(Direction.OUT)) {
-     			if (e.getLabel().equals("link")) {
-     				break;
-     			}
-     		}
-		}
-     	return null;
+     	return links;
 	}
 	
+	/**
+	 * Initialize the object. Open LinkStorage using given configuration file.
+	 * @param conf Path (absolute path for now) to configuration file.
+	 */
 	@Override
 	public void init(String conf) {
 		//TODO extract the DB location from properties
 		this.dbop = new GraphDBOperation(GraphDBConnection.getInstance(conf));
 	}
 
+	/**
+	 * Delete records of the links connected to the port specified by given DPID and port number.
+	 * @param dpid DPID of desired port.
+	 * @param port Port number of desired port.
+	 */
+	// TODO: Fix me
 	@Override
 	public void deleteLinksOnPort(Long dpid, short port) {
-		// TODO Auto-generated method stub
+		// BEGIN: Trial code
+		// author: Naoki Shiota
+		List<Link> linksToDelete = getLinks(dpid,port);
 		
+		for(Link l : linksToDelete) {
+			deleteLink(l);
+		}
+		// END: Trial code
 	}
 
+	/**
+	 * Get list of all links connected to the switch specified by given DPID.
+	 * @param dpid DPID of desired switch.
+	 * @return List of links. Empty list if no port was found.
+	 */
+	// TODO: Fix me
 	@Override
 	public List<Link> getLinks(String dpid) {
-		// TODO Auto-generated method stub
-		return null;
+		List<Link> links = new ArrayList<Link>();
+
+		return links;
 	}
 
+	/**
+	 * Get list of all links whose state is ACTIVE.
+	 * @return List of active links. Empty list if no port was found.
+	 */
 	public List<Link> getActiveLinks() {
 		Iterable<ISwitchObject> switches = dbop.getActiveSwitches();
 
@@ -248,10 +297,16 @@
 		}
 	}
 	
+	/**
+	 * Finalize the object.
+	 */
 	public void finalize() {
 		close();
 	}
 
+	/**
+	 * Close LinkStorage.
+	 */
 	@Override
 	public void close() {
 		// TODO Auto-generated method stub
diff --git a/src/test/java/net/floodlightcontroller/core/internal/TestDatabaseManager.java b/src/test/java/net/floodlightcontroller/core/internal/TestDatabaseManager.java
index 3d5e03b..431db71 100644
--- a/src/test/java/net/floodlightcontroller/core/internal/TestDatabaseManager.java
+++ b/src/test/java/net/floodlightcontroller/core/internal/TestDatabaseManager.java
@@ -5,18 +5,25 @@
 import java.io.FileNotFoundException;
 import java.io.IOException;
 import java.io.InputStream;
+import java.util.ArrayList;
 import java.util.Iterator;
+import java.util.List;
 import java.util.Set;
 
 import junit.framework.Assert;
 
+import net.floodlightcontroller.core.INetMapTopologyObjects.ISwitchObject;
+import net.floodlightcontroller.core.ISwitchStorage.SwitchState;
+
 import org.apache.commons.io.FileUtils;
 
 import com.thinkaurelius.titan.core.TitanFactory;
 import com.thinkaurelius.titan.core.TitanGraph;
+import com.tinkerpop.blueprints.Edge;
 import com.tinkerpop.blueprints.TransactionalGraph.Conclusion;
 import com.tinkerpop.blueprints.Vertex;
 import com.tinkerpop.blueprints.util.io.graphml.GraphMLReader;
+import com.tinkerpop.frames.FramedGraph;
 
 public class TestDatabaseManager {
 	private static final String testDbLocation = "/tmp/onos-testdb";
@@ -58,9 +65,20 @@
         Iterator<Vertex> it = titanGraph.getVertices("type", "port").iterator();
         while (it.hasNext()){
         	Vertex port = it.next();
-        	Integer portNum = (Integer) port.getProperty("number");
-        	port.setProperty("number", portNum.shortValue());
+        	if(port.getProperty("number").getClass() == Integer.class) {
+        		Integer portNum = port.getProperty("number");
+            	port.setProperty("number", portNum.shortValue());
+        	}
         }
+        
+		FramedGraph<TitanGraph> fg = new FramedGraph<TitanGraph>(titanGraph);
+		Iterable<ISwitchObject> switches =  fg.getVertices("type","switch",ISwitchObject.class);
+		List<ISwitchObject> activeSwitches = new ArrayList<ISwitchObject>();
+
+		for (ISwitchObject sw: switches) {
+			sw.setState(SwitchState.ACTIVE.toString());
+		}
+
         titanGraph.stopTransaction(Conclusion.SUCCESS);
 	}
 	
diff --git a/src/test/java/net/floodlightcontroller/linkdiscovery/internal/LinkDiscoveryManagerTest.java b/src/test/java/net/floodlightcontroller/linkdiscovery/internal/LinkDiscoveryManagerTest.java
index 6e99acd..0bf9ba0 100644
--- a/src/test/java/net/floodlightcontroller/linkdiscovery/internal/LinkDiscoveryManagerTest.java
+++ b/src/test/java/net/floodlightcontroller/linkdiscovery/internal/LinkDiscoveryManagerTest.java
@@ -50,6 +50,8 @@
 import net.floodlightcontroller.topology.ITopologyService;
 import net.floodlightcontroller.topology.NodePortTuple;
 import net.floodlightcontroller.topology.TopologyManager;
+import net.onrc.onos.registry.controller.IControllerRegistryService;
+import net.onrc.onos.registry.controller.StandaloneRegistry;
 
 /**
  *
@@ -58,6 +60,7 @@
 public class LinkDiscoveryManagerTest extends FloodlightTestCase {
 
     private TestLinkDiscoveryManager ldm;
+    private StandaloneRegistry srs;
     protected static Logger log = LoggerFactory.getLogger(LinkDiscoveryManagerTest.class);
     
     public class TestLinkDiscoveryManager extends LinkDiscoveryManager {
@@ -99,6 +102,7 @@
         ldm = new TestLinkDiscoveryManager();
         TopologyManager routingEngine = new TopologyManager();
         ldm.linkDiscoveryAware = new ArrayList<ILinkDiscoveryListener>();
+        srs = new StandaloneRegistry();
         MockThreadPoolService tp = new MockThreadPoolService();
         RestApiServer restApi = new RestApiServer();
         cntx.addService(IRestApiService.class, restApi);
@@ -108,13 +112,17 @@
         cntx.addService(ITopologyService.class, ldm);
         cntx.addService(IStorageSourceService.class, new MemoryStorageSource());
         cntx.addService(IFloodlightProviderService.class, getMockFloodlightProvider());
+        cntx.addService(IControllerRegistryService.class, srs);
+
         restApi.init(cntx);
         tp.init(cntx);
         routingEngine.init(cntx);
+        srs.init(cntx);
         ldm.init(cntx);
         restApi.startUp(cntx);
         tp.startUp(cntx);
         routingEngine.startUp(cntx);
+        srs.startUp(cntx);
         ldm.startUp(cntx);
 
         IOFSwitch sw1 = createMockSwitch(1L);
diff --git a/src/test/java/net/floodlightcontroller/linkdiscovery/internal/LinkStorageImplTest.java b/src/test/java/net/floodlightcontroller/linkdiscovery/internal/LinkStorageImplTest.java
index 857d091..0968fef 100644
--- a/src/test/java/net/floodlightcontroller/linkdiscovery/internal/LinkStorageImplTest.java
+++ b/src/test/java/net/floodlightcontroller/linkdiscovery/internal/LinkStorageImplTest.java
@@ -4,126 +4,632 @@
 import static org.junit.Assert.assertFalse;
 import static org.junit.Assert.assertTrue;
 
+import java.util.ArrayList;
 import java.util.Iterator;
 import java.util.List;
 
 import net.floodlightcontroller.core.internal.TestDatabaseManager;
+import net.floodlightcontroller.linkdiscovery.LinkInfo;
 import net.floodlightcontroller.routing.Link;
 import net.onrc.onos.ofcontroller.core.INetMapStorage.DM_OPERATION;
 import net.onrc.onos.ofcontroller.linkdiscovery.ILinkStorage;
 
+import org.easymock.EasyMock;
 import org.junit.After;
 import org.junit.Before;
 import org.junit.Ignore;
 import org.junit.Test;
+import org.junit.runner.RunWith;
+import org.openflow.protocol.OFPhysicalPort;
+import org.openflow.util.HexString;
+import org.powermock.api.easymock.PowerMock;
+import org.powermock.core.classloader.annotations.PrepareForTest;
+import org.powermock.modules.junit4.PowerMockRunner;
 
+import com.thinkaurelius.titan.core.TitanFactory;
 import com.thinkaurelius.titan.core.TitanGraph;
+import com.tinkerpop.blueprints.Direction;
+import com.tinkerpop.blueprints.Edge;
 import com.tinkerpop.blueprints.Vertex;
 import com.tinkerpop.gremlin.java.GremlinPipeline;
+import com.tinkerpop.pipes.PipeFunction;
+import com.tinkerpop.pipes.transform.PathPipe;
 
+@RunWith(PowerMockRunner.class)
+@PrepareForTest({TitanFactory.class})
 public class LinkStorageImplTest {
 	private static ILinkStorage linkStorage;
 	private static TitanGraph titanGraph;
 	
-	//TODO Future ideas:
-	//Test add links with CREATE and UPDATE
-	//Test adding existing link again
-	
+	//private static IController
+
+	/**
+	 * Setup code called before each tests.
+	 * Read test graph data and replace DB access by test graph data.
+	 * @throws Exception
+	 */
 	@Before
 	public void setUp() throws Exception{
+		TestDatabaseManager.deleteTestDatabase();
+
 		titanGraph = TestDatabaseManager.getTestDatabase();
 		TestDatabaseManager.populateTestData(titanGraph);
+
+		// replace return value of TitanFactory.open() to dummy DB created above
+		PowerMock.mockStatic(TitanFactory.class);
+		EasyMock.expect(TitanFactory.open((String)EasyMock.anyObject())).andReturn(titanGraph);
+		PowerMock.replay(TitanFactory.class);
 		
-		linkStorage = new TestableLinkStorageImpl(titanGraph);
+		linkStorage = new LinkStorageImpl();
+		
+		// initialize with dummy string
+		linkStorage.init("/dummy/path/to/db");
 	}
 	
+	/**
+	 * Closing code called after each tests.
+	 * Discard test graph data.
+	 * @throws Exception
+	 */
 	@After
-	public void tearDown() throws Exception {		
+	public void tearDown() throws Exception {
+		// finish code
+		linkStorage.close();
+		
 		titanGraph.shutdown();
+		TestDatabaseManager.deleteTestDatabase();
 	}
 	
-	/*
-	 * Add a link between port 1.102 and 2.104
-	 * i.e SEA switch port 3 to LAX switch port 1
+	// TODO: remove @Ignore after UPDATE method is implemented
+	/**
+	 * Test if update() can correctly updates LinkInfo for a Link.
+	 */
+	@Ignore @Test
+	public void testUpdate_UpdateSingleLink() {
+		Link linkToUpdate= createExistingLink();
+		long currentTime = System.currentTimeMillis();
+		LinkInfo infoToUpdate = createFeasibleLinkInfo(currentTime);
+		LinkInfo infoToVerify = createFeasibleLinkInfo(currentTime);
+
+		linkStorage.update(linkToUpdate, infoToUpdate, ILinkStorage.DM_OPERATION.UPDATE);
+		
+		doTestLinkHasStateOf(linkToUpdate, infoToVerify);
+	}
+	
+	/**
+	 * Test if update() can correctly creates a Link.
 	 */
 	@Test
-	public void testAddSingleLink(){
-		Link linkToAdd = new Link(Long.decode("0x0000000000000a01"), 3, Long.decode("0x0000000000000a02"), 1);
+	public void testUpdate_CreateSingleLink() {
+		Link linkToCreate = createFeasibleLink();
+		Link linkToVerify = createFeasibleLink();
 		
 		//Use the link storage API to add the link
-		linkStorage.update(linkToAdd, ILinkStorage.DM_OPERATION.INSERT);
+		linkStorage.update(linkToCreate, ILinkStorage.DM_OPERATION.CREATE);
+		doTestLinkIsInGraph(linkToVerify);
+
+		// Add same link
+		Link linkToCreateTwice = createFeasibleLink();
+		linkStorage.update(linkToCreateTwice, ILinkStorage.DM_OPERATION.CREATE);
 		
-		//Test if it was added correctly with the Gremlin API
-		GremlinPipeline<Vertex, Vertex> pipe = new GremlinPipeline<Vertex, Vertex>();
-		Iterator<Vertex> it = titanGraph.getVertices("dpid", "00:00:00:00:00:00:0a:01").iterator();
+		// this occurs assertion failure if there are two links in titanGraph
+		doTestLinkIsInGraph(linkToVerify);
+	}
+
+	/**
+	 * Test if update() can correctly inserts a Link.
+	 */
+	@Test
+	public void testUpdate_InsertSingleLink(){
+		Link linkToInsert = createFeasibleLink();
+		Link linkToVerify = createFeasibleLink();
 		
-		assertTrue(it.hasNext());
-		Vertex sw1 = it.next();
-		assertFalse(it.hasNext());
+		//Use the link storage API to add the link
+		linkStorage.update(linkToInsert, ILinkStorage.DM_OPERATION.INSERT);
+
+		doTestLinkIsInGraph(linkToVerify);
 		
-		pipe.start(sw1).out("on").has("number", (short)3).out("link").in("on");
-		
-		assertTrue(pipe.hasNext());
-		Vertex sw2 = pipe.next();
-		assertFalse(pipe.hasNext());
-		
-		//Check we ended up at the right vertex
-		assertEquals((String)sw2.getProperty("dpid"), "00:00:00:00:00:00:0a:02");
+		// Add same link
+		Link linkToInsertTwice = createFeasibleLink();
+		linkStorage.update(linkToInsertTwice, ILinkStorage.DM_OPERATION.INSERT);
+
+		// this occurs assertion failure if there are two links in titanGraph
+		doTestLinkIsInGraph(linkToVerify);
 	}
 	
-	//TODO enable once method is written
+	/**
+	 * Test if update() can correctly deletes a Link.
+	 */
+	@Test
+	public void testUpdate_DeleteSingleLink(){
+		Link linkToDelete = createExistingLink();
+		Link linkToVerify = createExistingLink();
+
+		// Test deletion of existing link
+		linkStorage.update(linkToDelete, DM_OPERATION.DELETE);
+		doTestLinkIsNotInGraph(linkToVerify);
+		
+		linkToDelete = createFeasibleLink();
+		linkToVerify = createFeasibleLink();
+
+		// Test deletion of not-existing link
+		linkStorage.update(linkToDelete, DM_OPERATION.DELETE);
+		doTestLinkIsNotInGraph(linkToVerify);
+	}
+
+	/**
+	 * Test if update() can correctly creates multiple Links.
+	 */
+	@Test
+	public void testUpdate_CreateLinks(){
+		List<Link> linksToCreate = createFeasibleLinks();
+		List<Link> linksToVerify = createFeasibleLinks();
+
+		// Test creation of new links
+		linkStorage.update(linksToCreate, ILinkStorage.DM_OPERATION.CREATE);
+		for(Link l : linksToVerify) {
+			doTestLinkIsInGraph(l);
+		}
+		
+		// Test creation of existing links
+		linksToCreate = createFeasibleLinks();
+		linkStorage.update(linksToCreate, ILinkStorage.DM_OPERATION.CREATE);
+		for(Link l : linksToVerify) {
+			doTestLinkIsInGraph(l);
+		}
+	}
+	
+	/**
+	 * Test if update() can handle mixture of normal/abnormal input for creation of Links.
+	 */
+	@Test
+	public void testUpdate_CreateLinks_Mixuture(){
+		List<Link> linksToCreate = new ArrayList<Link>();
+		linksToCreate.add(createFeasibleLink());
+		linksToCreate.add(createExistingLink());
+		
+		// Test creation of mixture of new/existing links
+		linkStorage.update(linksToCreate, ILinkStorage.DM_OPERATION.CREATE);
+		doTestLinkIsInGraph(createFeasibleLink());
+		doTestLinkIsInGraph(createExistingLink());
+	}
+
+	/**
+	 * Test if update() can correctly inserts multiple Links.
+	 */
+	@Test
+	public void testUpdate_InsertLinks(){
+		List<Link> linksToInsert = createFeasibleLinks();
+		List<Link> linksToVerify = createFeasibleLinks();
+		
+		// Test insertion of new links
+		linkStorage.update(linksToInsert, ILinkStorage.DM_OPERATION.INSERT);
+		for(Link l : linksToVerify) {
+			doTestLinkIsInGraph(l);
+		}
+		
+		// Test insertion of existing links
+		linksToInsert = createFeasibleLinks();
+		linkStorage.update(linksToInsert, ILinkStorage.DM_OPERATION.INSERT);
+		for(Link l : linksToVerify) {
+			doTestLinkIsInGraph(l);
+		}
+	}
+	
+	/**
+	 * Test if update() can handle mixture of normal/abnormal input for creation of Links.
+	 */
+	@Test
+	public void testUpdate_InsertLinks_Mixuture(){
+		List<Link> linksToInsert = new ArrayList<Link>();
+		linksToInsert.add(createFeasibleLink());
+		linksToInsert.add(createExistingLink());
+		
+		// Test insertion of mixture of new/existing links
+		linkStorage.update(linksToInsert, ILinkStorage.DM_OPERATION.INSERT);
+		doTestLinkIsInGraph(createFeasibleLink());
+		doTestLinkIsInGraph(createExistingLink());
+	}
+
+	/**
+	 * Test if update() can correctly deletes multiple Links.
+	 */
+	@Test
+	public void testUpdate_DeleteLinks(){
+		List<Link> linksToDelete = createExistingLinks();
+		List<Link> linksToVerify = createExistingLinks();
+		
+		// Test deletion of existing links
+		linkStorage.update(linksToDelete, ILinkStorage.DM_OPERATION.DELETE);
+		for(Link l : linksToVerify) {
+			doTestLinkIsNotInGraph(l);
+		}
+		
+		// Test deletion of not-existing links
+		linksToDelete = createExistingLinks();
+		linkStorage.update(linksToDelete, ILinkStorage.DM_OPERATION.DELETE);
+		for(Link l : linksToVerify) {
+			doTestLinkIsNotInGraph(l);
+		}
+	}
+	
+	/**
+	 * Test if update() can handle mixture of normal/abnormal input for deletion of Links.
+	 */
+	@Test
+	public void testUpdate_DeleteLinks_Mixuture(){
+		List<Link> linksToDelete = new ArrayList<Link>();
+		linksToDelete.add(createFeasibleLink());
+		linksToDelete.add(createExistingLink());
+		
+		// Test deletion of mixture of new/existing links
+		linkStorage.update(linksToDelete, ILinkStorage.DM_OPERATION.DELETE);
+		doTestLinkIsNotInGraph(createFeasibleLink());
+		doTestLinkIsNotInGraph(createExistingLink());
+	}
+	
+	// TODO: remove @Ignore after UPDATE method is implemented
+	/**
+	 * Test if updateLink() can correctly updates LinkInfo for a Link.
+	 */
 	@Ignore @Test
-	public void testGetLinks(){
-		//TODO Make sure this works when the implementation is written
-		List<Link> list = linkStorage.getLinks(Long.decode("0x0000000000000a01"), (short)2);
+	public void testUpdateLink_Update() {
+		Link linkToUpdate= createExistingLink();
+		long currentTime = System.currentTimeMillis();
+		LinkInfo infoToUpdate = createFeasibleLinkInfo(currentTime);
+		LinkInfo infoToVerify = createFeasibleLinkInfo(currentTime);
+
+		linkStorage.updateLink(linkToUpdate, infoToUpdate, ILinkStorage.DM_OPERATION.UPDATE);
+		
+		doTestLinkHasStateOf(linkToUpdate, infoToVerify);
+	}
+	
+	/**
+	 * Test if updateLink() can correctly creates a Link.
+	 */
+	@Test
+	public void testUpdateLink_Create() {
+		Link linkToCreate = createFeasibleLink();
+		Link linkToVerify = createFeasibleLink();
+		
+		//Use the link storage API to add the link
+		linkStorage.updateLink(linkToCreate, null, ILinkStorage.DM_OPERATION.CREATE);
+		doTestLinkIsInGraph(linkToVerify);
+
+		// Add same link
+		Link linkToCreateTwice = createFeasibleLink();
+		linkStorage.updateLink(linkToCreateTwice, null, ILinkStorage.DM_OPERATION.CREATE);
+		
+		// this occurs assertion failure if there are two links in titanGraph
+		doTestLinkIsInGraph(linkToVerify);
+	}
+	
+	/**
+	 * Test if updateLink() can correctly inserts a Link.
+	 */
+	@Test
+	public void testUpdateLink_Insert() {
+		Link linkToInsert = createFeasibleLink();
+		Link linkToVerify = createFeasibleLink();
+		
+		//Use the link storage API to add the link
+		linkStorage.updateLink(linkToInsert, null, ILinkStorage.DM_OPERATION.INSERT);
+
+		doTestLinkIsInGraph(linkToVerify);
+		
+		// Add same link
+		Link linkToInsertTwice = createFeasibleLink();
+		linkStorage.updateLink(linkToInsertTwice, null, ILinkStorage.DM_OPERATION.INSERT);
+
+		// this occurs assertion failure if there are two links in titanGraph
+		doTestLinkIsInGraph(linkToVerify);
+	}
+	
+	// TODO: Check if addOrUpdateLink() should accept DELETE operation. If not, remove this test.
+	/**
+	 * Test if updateLink() can correctly deletes a Link.
+	 */
+	@Ignore @Test
+	public void testUpdateLink_Delete() {
+		Link linkToDelete = createExistingLink();
+		Link linkToVerify = createExistingLink();
+
+		// Test deletion of existing link
+		linkStorage.updateLink(linkToDelete, null, DM_OPERATION.DELETE);
+		doTestLinkIsNotInGraph(linkToVerify);
+		
+		linkToDelete = createFeasibleLink();
+		linkToVerify = createFeasibleLink();
+
+		// Test deletion of not-existing link
+		linkStorage.updateLink(linkToDelete, null, DM_OPERATION.DELETE);
+		doTestLinkIsNotInGraph(linkToVerify);
+	}
+	
+	/**
+	 * Test if getLinks() can correctly return Links connected to specific DPID and port.
+	 */
+	@Test
+	public void testGetLinks_ByDpidPort(){
+		Link linkToVerify = createExistingLink();
+		Long dpid = linkToVerify.getSrc();
+		short port = (short)linkToVerify.getSrcPort();
+		
+		List<Link> list = linkStorage.getLinks(dpid, port);
 		
 		assertEquals(list.size(), 1);
 		
 		Link l = list.get(0);
-		assertEquals(l.getSrc(), 2561L);
-		assertEquals(l.getSrcPort(), (short)2);
-		assertEquals(l.getDst(), 2563L);
-		assertEquals(l.getDstPort(), (short)1);
+		assertEquals(l.getSrc(), linkToVerify.getSrc());
+		assertEquals(l.getSrcPort(), linkToVerify.getSrcPort());
+		assertEquals(l.getDst(), linkToVerify.getDst());
+		assertEquals(l.getDstPort(), linkToVerify.getDstPort());
+		
+		Link linkToVerifyNot = createFeasibleLink();
+		
+		List<Link> list2 = linkStorage.getLinks(linkToVerifyNot.getSrc(), (short)linkToVerifyNot.getSrcPort());
+		
+		assertEquals(list2.size(), 0);
 	}
 	
-	//TODO enable once method is written
-	@Ignore @Test
-	public void testUpdateDelete(){
-		Link linkToDelete = new Link(Long.decode("0x0000000000000a01"), 2, Long.decode("0x0000000000000a03"), 1);
+	/**
+	 * Test if getLinks() can correctly return Links connected to specific MAC address.
+	 */
+	@Test
+	public void testGetLinks_ByString() {
+		Link linkToVeryfy = createExistingLink();
+		String dpid = HexString.toHexString(linkToVeryfy.getSrc());
 		
-		linkStorage.update(linkToDelete, DM_OPERATION.DELETE);
-		
-		//Test if it was deleted correctly with the Gremlin API
-		GremlinPipeline<Vertex, Vertex> pipe = new GremlinPipeline<Vertex, Vertex>();
-		Iterator<Vertex> it = titanGraph.getVertices("dpid", "00:00:00:00:00:00:0a:01").iterator();
-		
-		assertTrue(it.hasNext());
-		Vertex sw1 = it.next();
-		assertFalse(it.hasNext());
-		
-		pipe.start(sw1).out("on").has("number", 2).out("link");
-		
-		assertFalse(pipe.hasNext());
+		List<Link> links = linkStorage.getLinks(dpid);
+		assertTrue(links.contains(linkToVeryfy));
+
+		Link linkToVerifyNot = createFeasibleLink();
+		assertFalse(links.contains(linkToVerifyNot));
 	}
 	
-	//TODO enable once method is written
-	@Ignore @Test
+	/**
+	 * Test if deleteLink() can correctly delete a Link.
+	 */
+	@Test
+	public void testDeleteLink() {
+		// Deletion of existing link
+		Link linkToDelete = createExistingLink();
+		Link linkToVerify = createExistingLink();
+		
+		linkStorage.deleteLink(linkToDelete);
+		doTestLinkIsNotInGraph(linkToVerify);
+		
+		// Deletion of not existing link
+		linkToDelete = createFeasibleLink();
+		linkToVerify = createFeasibleLink();
+		
+		linkStorage.deleteLink(linkToDelete);
+		doTestLinkIsNotInGraph(linkToVerify);
+	}
+	
+	/**
+	 * Test if deleteLinks() can correctly delete Links.
+	 */
+	@Test
 	public void testDeleteLinks(){
-		//TODO Make sure this works when the implementation is written
+		List<Link> linksToDelete = createExistingLinks();
+		List<Link> linksToVerify = createExistingLinks();
 		
-		linkStorage.deleteLinksOnPort(Long.decode("0x0000000000000a01"), (short)2);
+		linkStorage.deleteLinks(linksToDelete);
+		for(Link l : linksToVerify) {
+			doTestLinkIsNotInGraph(l);
+		}
+	}
+	
+	/**
+	 * Test if deleteLinks() can handle mixture of normal/abnormal input.
+	 */
+	@Test
+	public void testDeleteLinks_Mixture(){
+		List<Link> linksToDelete = new ArrayList<Link>();
+		linksToDelete.add(createFeasibleLink());
+		linksToDelete.add(createExistingLink());
 		
-		//Test if it was deleted correctly with the Gremlin API
-		GremlinPipeline<Vertex, Vertex> pipe = new GremlinPipeline<Vertex, Vertex>();
-		Iterator<Vertex> it = titanGraph.getVertices("dpid", "00:00:00:00:00:00:0a:01").iterator();
+		// Test deletion of mixture of new/existing links
+		linkStorage.deleteLinks(linksToDelete);
+		doTestLinkIsNotInGraph(createFeasibleLink());
+		doTestLinkIsNotInGraph(createExistingLink());
+	}
+
+	/**
+	 * Test if getActiveLinks() can correctly return active Links.
+	 */
+	@Test
+	public void testGetActiveLinks() {
+		Link existingLink = createExistingLink();
+		Link notExistingLink = createFeasibleLink();
+
+		List<Link> links = linkStorage.getActiveLinks();
 		
+		assertTrue(links.contains(existingLink));
+		assertFalse(links.contains(notExistingLink));
+	}
+	
+	/**
+	 * Test if deleteLinksOnPort() can delete Links.
+	 */
+	@Test
+	public void testDeleteLinksOnPort() {
+		Link linkToDelete = createExistingLink();
+		Link linkToVerify = createExistingLink();
+		
+		linkStorage.deleteLinksOnPort(linkToDelete.getSrc(), linkToDelete.getSrcPort());
+		
+		doTestLinkIsNotInGraph(linkToVerify);
+	}
+
+	/**
+	 * Test if titanGraph has specific link
+	 * @param link 
+	 */
+	private void doTestLinkIsInGraph(Link link) {
+		String src_dpid = HexString.toHexString(link.getSrc());
+		String dst_dpid = HexString.toHexString(link.getDst());
+		short src_port = link.getSrcPort();
+		short dst_port = link.getDstPort();
+		
+		Iterator<Vertex> it = titanGraph.getVertices("dpid", src_dpid).iterator();
+		
+		// Test if just one switch is found in the graph
 		assertTrue(it.hasNext());
-		Vertex sw1 = it.next();
+		Vertex sw = it.next();
 		assertFalse(it.hasNext());
 		
-		pipe.start(sw1).out("on").has("number", 2).out("link");
+		GremlinPipeline<Vertex, Vertex> pipe = new GremlinPipeline<Vertex, Vertex>();
+		pipe.start(sw).out("on").has("number", src_port).out("link").has("number", dst_port).in("on").has("dpid", dst_dpid);
 		
+		// Test if just one link is found in the graph
+		assertTrue(pipe.hasNext());
+		pipe.next();
 		assertFalse(pipe.hasNext());
 	}
 	
+	/**
+	 * Test if titanGraph doesn't have specific link
+	 * @param link
+	 */
+	private void doTestLinkIsNotInGraph(Link link) {
+		String src_dpid = HexString.toHexString(link.getSrc());
+		String dst_dpid = HexString.toHexString(link.getDst());
+		short src_port = link.getSrcPort();
+		short dst_port = link.getDstPort();
+		
+		Iterator<Vertex> it = titanGraph.getVertices("dpid", src_dpid).iterator();
+		
+		// Test if just one switch is found in the graph
+		assertTrue(it.hasNext());
+		Vertex sw = it.next();
+		assertFalse(it.hasNext());
+		
+		GremlinPipeline<Vertex, Vertex> pipe = new GremlinPipeline<Vertex, Vertex>();
+		pipe.start(sw).out("on").has("number", src_port).out("link").has("number", dst_port).in("on").has("dpid", dst_dpid);
+		
+		// Test if no link is found in the graph
+		assertFalse(pipe.hasNext());
+	}
+	
+	/**
+	 * Test if titanGraph has specific Link with specific LinkInfo
+	 * @param link 
+	 */
+	private void doTestLinkHasStateOf(Link link, LinkInfo info) {
+		String src_dpid = HexString.toHexString(link.getSrc());
+		String dst_dpid = HexString.toHexString(link.getDst());
+		short src_port = link.getSrcPort();
+		short dst_port = link.getDstPort();
+		
+		Iterator<Vertex> it = titanGraph.getVertices("dpid", src_dpid).iterator();
+		
+		// Test if just one switch is found in the graph
+		assertTrue(it.hasNext());
+		Vertex sw = it.next();
+		assertFalse(it.hasNext());
+		
+		GremlinPipeline<Vertex, Edge> pipe = new GremlinPipeline<Vertex, Edge>();
+		pipe.start(sw);
+		pipe.enablePath();
+		pipe.out("on").has("number", src_port).out("link").has("number", dst_port).in("on").has("dpid", dst_dpid)
+			.path().step(new PipeFunction<PathPipe<Vertex>, Edge>() {
+			@Override
+			public Edge compute(PathPipe<Vertex> pipepath) {
+				List<Vertex> V = pipepath.next();
+
+				Vertex port_src = V.get(1);
+				Vertex port_dst = V.get(2);
+				
+				for(Edge e : port_src.getEdges(Direction.OUT)) {
+					if(e.getVertex(Direction.IN).equals(port_dst)) {
+						return e;
+					}
+				}
+				
+				return null;
+			}
+		});
+		
+		// Test if just one link is found in the graph
+		assertTrue(pipe.hasNext());
+		Edge edge = pipe.next();
+		assertTrue(edge != null);
+		assertFalse(pipe.hasNext());
+
+		// TODO: implement test code to check if update is correctly done.
+		assertTrue(false);
+	}
+
+
+	//----------------- Creation of test data -----------------------
+	/**
+	 * Returns new Link object which has information of existing link in titanGraph
+	 * @return new Link object
+	 */
+	private Link createExistingLink() {
+		// Link from SEA switch port 2 to CHI switch port 1
+		return new Link(Long.decode("0x0000000000000a01"), 2, Long.decode("0x0000000000000a03"), 1);
+	}
+	
+	/**
+	 * Returns new Link object which has information of not-existing but feasible link in titanGraph
+	 * @return new Link object
+	 */
+	private Link createFeasibleLink() {
+		// Link from SEA switch port 1 to LAX switch port 1
+		return new Link(Long.decode("0x0000000000000a01"), 4, Long.decode("0x0000000000000a02"), 1);
+	}
+	
+	// make NO sense while test-network data doesn't define physical network (i.e. any link is feasible)
+	@SuppressWarnings("unused")
+	private Link createInfeasibleLink() {
+		return new Link(Long.decode("0x0000000000000a01"), 1, Long.decode("0x0000000000000a02"), 1);
+	}
+
+	/**
+	 * Returns list of Link objects which all has information of existing link in titanGraph
+	 * @return ArrayList of new Link objects
+	 */
+	private List<Link> createExistingLinks() {
+		List<Link> links = new ArrayList<Link>();
+		// Link from SEA switch port 2 to CHI switch port 1
+		links.add(new Link(Long.decode("0x0000000000000a01"), 2, Long.decode("0x0000000000000a03"), 1));
+		// Link from LAX switch port 1 to SEA switch port 3
+		links.add(new Link(Long.decode("0x0000000000000a02"), 1, Long.decode("0x0000000000000a01"), 3));
+		return links;
+	}
+	
+	/**
+	 * Returns list of Link objects which all has information of not-existing but feasible link
+	 * @return ArrayList of new Link objects
+	 */
+	private List<Link> createFeasibleLinks() {
+		List<Link> links = new ArrayList<Link>();
+		// Link from CHI switch port 4 to NYC switch port 3
+		links.add(new Link(Long.decode("0x0000000000000a03"), 4, Long.decode("0x0000000000000a05"), 3));
+		// Link from SEA switch port 4 to LAX switch port 1
+		links.add(new Link(Long.decode("0x0000000000000a01"), 4, Long.decode("0x0000000000000a02"), 1));
+		return links;
+	}
+	
+	/**
+	 * Returns new LinkInfo object with convenient values.
+	 * @return LinkInfo object
+	 */
+	private LinkInfo createFeasibleLinkInfo(long time) {
+		long time_first = time;
+		long time_last_lldp = time + 50;
+		long time_last_bddp = time + 100;
+		int state_src = OFPhysicalPort.OFPortState.OFPPS_STP_FORWARD.getValue();
+		int state_dst = OFPhysicalPort.OFPortState.OFPPS_STP_LISTEN.getValue();
+
+		return new LinkInfo(time_first,
+				time_last_lldp,
+				time_last_bddp,
+				state_src,
+				state_dst);
+	}
+	//---------------------------------------------------------------
 }
