diff --git a/core/api/src/test/java/org/onosproject/store/service/TestAtomicCounter.java b/core/api/src/test/java/org/onosproject/store/primitives/AsyncAtomicCounterAdapter.java
similarity index 83%
rename from core/api/src/test/java/org/onosproject/store/service/TestAtomicCounter.java
rename to core/api/src/test/java/org/onosproject/store/primitives/AsyncAtomicCounterAdapter.java
index c09c223..36cb9f1 100644
--- a/core/api/src/test/java/org/onosproject/store/service/TestAtomicCounter.java
+++ b/core/api/src/test/java/org/onosproject/store/primitives/AsyncAtomicCounterAdapter.java
@@ -1,5 +1,5 @@
 /*
- * Copyright 2015-present Open Networking Foundation
+ * Copyright 2018-present Open Networking Foundation
  *
  * Licensed under the Apache License, Version 2.0 (the "License");
  * you may not use this file except in compliance with the License.
@@ -13,7 +13,10 @@
  * See the License for the specific language governing permissions and
  * limitations under the License.
  */
-package org.onosproject.store.service;
+package org.onosproject.store.primitives;
+
+import org.onosproject.store.service.AsyncAtomicCounter;
+import org.onosproject.store.service.AtomicCounterBuilder;
 
 import java.util.concurrent.CompletableFuture;
 import java.util.concurrent.atomic.AtomicLong;
@@ -21,15 +24,15 @@
 /**
  * Test implementation of atomic counter.
  */
-public final class TestAtomicCounter implements AsyncAtomicCounter {
-    final AtomicLong value;
+public class AsyncAtomicCounterAdapter implements AsyncAtomicCounter {
+    private final AtomicLong value;
 
     @Override
     public String name() {
         return null;
     }
 
-    private TestAtomicCounter() {
+    AsyncAtomicCounterAdapter() {
         value = new AtomicLong();
     }
 
@@ -76,7 +79,7 @@
     public static class Builder extends AtomicCounterBuilder {
         @Override
         public AsyncAtomicCounter build() {
-            return new TestAtomicCounter();
+            return new AsyncAtomicCounterAdapter();
         }
     }
 }
diff --git a/core/api/src/test/java/org/onosproject/store/primitives/AsyncAtomicCounterMapAdapter.java b/core/api/src/test/java/org/onosproject/store/primitives/AsyncAtomicCounterMapAdapter.java
new file mode 100644
index 0000000..f9a08f8
--- /dev/null
+++ b/core/api/src/test/java/org/onosproject/store/primitives/AsyncAtomicCounterMapAdapter.java
@@ -0,0 +1,138 @@
+/*
+ * Copyright 2018-present Open Networking Foundation
+ *
+ * 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.store.primitives;
+
+import org.onosproject.store.service.AsyncAtomicCounterMap;
+
+import java.util.HashMap;
+import java.util.Map;
+import java.util.concurrent.CompletableFuture;
+
+public class AsyncAtomicCounterMapAdapter<K> implements AsyncAtomicCounterMap<K> {
+    private Map<K, Long> map = new HashMap<>();
+
+    @Override
+    public CompletableFuture<Long> incrementAndGet(K key) {
+        Long value = map.getOrDefault(key, 0L) + 1;
+        map.put(key, value);
+        return CompletableFuture.completedFuture(value);
+
+    }
+
+    @Override
+    public CompletableFuture<Long> decrementAndGet(K key) {
+        Long value = map.getOrDefault(key, 0L) - 1;
+        map.put(key, value);
+        return CompletableFuture.completedFuture(value);
+
+    }
+
+    @Override
+    public CompletableFuture<Long> getAndIncrement(K key) {
+        Long value = map.getOrDefault(key, 0L);
+        map.put(key, value + 1);
+        return CompletableFuture.completedFuture(value);
+
+    }
+
+    @Override
+    public CompletableFuture<Long> getAndDecrement(K key) {
+        Long value = map.getOrDefault(key, 0L);
+        map.put(key, value - 1);
+        return CompletableFuture.completedFuture(value);
+    }
+
+    @Override
+    public CompletableFuture<Long> addAndGet(K key, long delta) {
+        Long value = map.getOrDefault(key, 0L) + delta;
+        map.put(key, value);
+        return CompletableFuture.completedFuture(value);
+    }
+
+    @Override
+    public CompletableFuture<Long> getAndAdd(K key, long delta) {
+        Long value = map.getOrDefault(key, 0L);
+        map.put(key, value + delta);
+        return CompletableFuture.completedFuture(value);
+    }
+
+    @Override
+    public CompletableFuture<Long> get(K key) {
+        Long value = map.getOrDefault(key, 0L);
+        return CompletableFuture.completedFuture(value);
+    }
+
+    @Override
+    public CompletableFuture<Long> put(K key, long newValue) {
+        Long value = map.getOrDefault(key, 0L);
+        map.put(key, newValue);
+        return CompletableFuture.completedFuture(value);
+    }
+
+    @Override
+    public CompletableFuture<Long> putIfAbsent(K key, long newValue) {
+        Long value = map.putIfAbsent(key, newValue);
+        if (value == null) {
+            value = 0L;
+        }
+        return CompletableFuture.completedFuture(value);
+    }
+
+    @Override
+    public CompletableFuture<Boolean> replace(K key, long expectedOldValue, long newValue) {
+        boolean value = map.replace(key, expectedOldValue, newValue);
+        return CompletableFuture.completedFuture(value);
+    }
+
+    @Override
+    public CompletableFuture<Long> remove(K key) {
+        Long value = map.remove(key);
+        return CompletableFuture.completedFuture(value);
+    }
+
+    @Override
+    public CompletableFuture<Boolean> remove(K key, long value) {
+        boolean result = map.remove(key, value);
+        return CompletableFuture.completedFuture(result);
+    }
+
+    @Override
+    public CompletableFuture<Integer> size() {
+        int value = map.size();
+        return CompletableFuture.completedFuture(value);
+    }
+
+    @Override
+    public CompletableFuture<Boolean> isEmpty() {
+        boolean value = map.isEmpty();
+        return CompletableFuture.completedFuture(value);
+    }
+
+
+
+    @Override
+    public CompletableFuture<Void> clear() {
+        map.clear();
+        return CompletableFuture.completedFuture(null);
+
+    }
+
+    @Override
+    public String name() {
+        return null;
+    }
+}
diff --git a/core/api/src/test/java/org/onosproject/store/primitives/AsyncConsistentTreeMapAdapter.java b/core/api/src/test/java/org/onosproject/store/primitives/AsyncConsistentTreeMapAdapter.java
new file mode 100644
index 0000000..9f6da1a
--- /dev/null
+++ b/core/api/src/test/java/org/onosproject/store/primitives/AsyncConsistentTreeMapAdapter.java
@@ -0,0 +1,370 @@
+/*
+ * Copyright 2018-present Open Networking Foundation
+ *
+ * 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.store.primitives;
+
+import com.google.common.collect.Maps;
+import org.onosproject.core.ApplicationId;
+import org.onosproject.store.service.AsyncConsistentTreeMap;
+import org.onosproject.store.service.ConsistentMap;
+import org.onosproject.store.service.ConsistentTreeMap;
+import org.onosproject.store.service.MapEventListener;
+import org.onosproject.store.service.TransactionLog;
+import org.onosproject.store.service.Version;
+import org.onosproject.store.service.Versioned;
+
+import java.util.AbstractMap;
+import java.util.Collection;
+import java.util.HashMap;
+import java.util.Map;
+import java.util.NavigableMap;
+import java.util.NavigableSet;
+import java.util.Set;
+import java.util.TreeMap;
+import java.util.concurrent.CompletableFuture;
+import java.util.concurrent.Executor;
+import java.util.function.BiFunction;
+import java.util.function.Consumer;
+import java.util.function.Function;
+import java.util.function.Predicate;
+import java.util.stream.Collectors;
+
+public class AsyncConsistentTreeMapAdapter<V> implements AsyncConsistentTreeMap<V> {
+
+    private TreeMap<String, V> map = Maps.newTreeMap();
+
+    private CompletableFuture<Map.Entry<String, Versioned<V>>> makeVersionedEntry(Map.Entry<String, V> entry) {
+        return CompletableFuture.completedFuture(
+                new AbstractMap.SimpleImmutableEntry<>(entry.getKey(),
+                                                       makeVersioned(entry.getValue())));
+    }
+
+    private CompletableFuture<Versioned<V>> makeVersionedFuture(V value) {
+        return CompletableFuture.completedFuture(makeVersioned(value));
+    }
+
+    private Versioned<V> makeVersioned(V value) {
+        return new Versioned<>(value, 1);
+    }
+
+    @Override
+    public CompletableFuture<String> firstKey() {
+        return CompletableFuture.completedFuture(map.firstKey());
+    }
+
+    @Override
+    public CompletableFuture<String> lastKey() {
+        return CompletableFuture.completedFuture(map.lastKey());
+    }
+
+    @Override
+    public CompletableFuture<Map.Entry<String, Versioned<V>>> ceilingEntry(String key) {
+        return makeVersionedEntry(map.ceilingEntry(key));
+    }
+
+    @Override
+    public CompletableFuture<Map.Entry<String, Versioned<V>>> floorEntry(String key) {
+        return makeVersionedEntry(map.floorEntry(key));
+    }
+
+    @Override
+    public CompletableFuture<Map.Entry<String, Versioned<V>>> higherEntry(String key) {
+        return makeVersionedEntry(map.higherEntry(key));
+    }
+
+    @Override
+    public CompletableFuture<Map.Entry<String, Versioned<V>>> lowerEntry(String key) {
+        return makeVersionedEntry(map.lowerEntry(key));
+    }
+
+    @Override
+    public CompletableFuture<Map.Entry<String, Versioned<V>>> firstEntry() {
+        return makeVersionedEntry(map.firstEntry());
+    }
+
+    @Override
+    public CompletableFuture<Map.Entry<String, Versioned<V>>> lastEntry() {
+        return makeVersionedEntry(map.lastEntry());
+    }
+
+    @Override
+    public CompletableFuture<Map.Entry<String, Versioned<V>>> pollFirstEntry() {
+        return makeVersionedEntry(map.pollFirstEntry());
+    }
+
+    @Override
+    public CompletableFuture<Map.Entry<String, Versioned<V>>> pollLastEntry() {
+        return makeVersionedEntry(map.pollLastEntry());
+    }
+
+    @Override
+    public CompletableFuture<String> lowerKey(String key) {
+        return CompletableFuture.completedFuture(map.lowerKey(key));
+    }
+
+    @Override
+    public CompletableFuture<String> floorKey(String key) {
+        return CompletableFuture.completedFuture(map.floorKey(key));
+    }
+
+    @Override
+    public CompletableFuture<String> ceilingKey(String key) {
+        return CompletableFuture.completedFuture(map.ceilingKey(key));
+    }
+
+    @Override
+    public CompletableFuture<String> higherKey(String key) {
+        return CompletableFuture.completedFuture(map.higherKey(key));
+    }
+
+    @Override
+    public CompletableFuture<NavigableSet<String>> navigableKeySet() {
+        return CompletableFuture.completedFuture(map.navigableKeySet());
+    }
+
+    @Override
+    public CompletableFuture<NavigableMap<String, V>> subMap(String upperKey, String lowerKey,
+                                                             boolean inclusiveUpper, boolean inclusiveLower) {
+        NavigableMap<String, V> subMap = map.subMap(upperKey, inclusiveLower, lowerKey, inclusiveLower);
+        return CompletableFuture.completedFuture(subMap);
+    }
+
+    @Override
+    public ConsistentTreeMap<V> asTreeMap() {
+        return null;
+    }
+
+    @Override
+    public ConsistentTreeMap<V> asTreeMap(long timeoutMillis) {
+        return null;
+    }
+
+    @Override
+    public Type primitiveType() {
+        return null;
+    }
+
+    @Override
+    public CompletableFuture<Integer> size() {
+        return CompletableFuture.completedFuture(map.size());
+    }
+
+    @Override
+    public CompletableFuture<Boolean> isEmpty() {
+        return CompletableFuture.completedFuture(map.isEmpty());
+    }
+
+    @Override
+    public CompletableFuture<Boolean> containsKey(String key) {
+        return CompletableFuture.completedFuture(map.containsKey(key));
+    }
+
+    @Override
+    public CompletableFuture<Boolean> containsValue(V value) {
+        return CompletableFuture.completedFuture(map.containsValue(value));
+    }
+
+    @Override
+    public CompletableFuture<Versioned<V>> get(String key) {
+        return makeVersionedFuture(map.get(key));
+    }
+
+    @Override
+    public CompletableFuture<Versioned<V>> getOrDefault(String key, V defaultValue) {
+        return makeVersionedFuture(map.getOrDefault(key, defaultValue));
+    }
+
+    @Override
+    public CompletableFuture<Versioned<V>>
+           computeIfAbsent(String key, Function<? super String, ? extends V> mappingFunction) {
+        return makeVersionedFuture(map.computeIfAbsent(key, mappingFunction));
+    }
+
+    @Override
+    public CompletableFuture<Versioned<V>>
+           computeIfPresent(String key, BiFunction<? super String, ? super V, ? extends V> remappingFunction) {
+        return makeVersionedFuture(map.computeIfPresent(key, remappingFunction));
+    }
+
+    @Override
+    public CompletableFuture<Versioned<V>>
+           compute(String key, BiFunction<? super String, ? super V, ? extends V> remappingFunction) {
+        return makeVersionedFuture(map.compute(key, remappingFunction));
+    }
+
+    @Override
+    public CompletableFuture<Versioned<V>>
+    computeIf(String key, Predicate<? super V> condition,
+              BiFunction<? super String, ? super V, ? extends V> remappingFunction) {
+
+        V value = map.get(key);
+
+        if (condition.test(value)) {
+            value = map.compute(key, remappingFunction);
+        }
+        return makeVersionedFuture(value);
+    }
+
+    @Override
+    public CompletableFuture<Versioned<V>> put(String key, V value) {
+        return makeVersionedFuture(map.put(key, value));
+    }
+
+    @Override
+    public CompletableFuture<Versioned<V>> putAndGet(String key, V value) {
+        return makeVersionedFuture(map.put(key, value));
+    }
+
+    @Override
+    public CompletableFuture<Versioned<V>> remove(String key) {
+        return makeVersionedFuture(map.remove(key));
+    }
+
+    @Override
+    public CompletableFuture<Void> clear() {
+        map.clear();
+        return CompletableFuture.completedFuture(null);
+    }
+
+    @Override
+    public CompletableFuture<Set<String>> keySet() {
+        return CompletableFuture.completedFuture(map.keySet());
+    }
+
+    @Override
+    public CompletableFuture<Collection<Versioned<V>>> values() {
+        Set<Versioned<V>> valuesAsVersionedCollection =
+                map.values().stream().map(this::makeVersioned)
+                        .collect(Collectors.toSet());
+        return CompletableFuture.completedFuture(valuesAsVersionedCollection);
+    }
+
+    @Override
+    public CompletableFuture<Set<Map.Entry<String, Versioned<V>>>> entrySet() {
+        Map<String, Versioned<V>> valuesAsVersionedMap = new HashMap<>();
+        map.forEach((key, value) ->
+                valuesAsVersionedMap.put(key, makeVersioned(value))
+        );
+        return CompletableFuture.completedFuture(valuesAsVersionedMap.entrySet());
+    }
+
+    @Override
+    public CompletableFuture<Versioned<V>> putIfAbsent(String key, V value) {
+        return makeVersionedFuture(map.putIfAbsent(key, value));
+    }
+
+    @Override
+    public CompletableFuture<Boolean> remove(String key, V value) {
+        return CompletableFuture.completedFuture(map.remove(key, value));
+    }
+
+    @Override
+    public CompletableFuture<Boolean> remove(String key, long version) {
+        Object value = map.remove(key);
+        return CompletableFuture.completedFuture(value != null);
+    }
+
+    @Override
+    public CompletableFuture<Versioned<V>> replace(String key, V value) {
+        return makeVersionedFuture(map.replace(key, value));
+    }
+
+    @Override
+    public CompletableFuture<Boolean> replace(String key, V oldValue, V newValue) {
+        return CompletableFuture.completedFuture(map.replace(key, oldValue, newValue));
+    }
+
+    @Override
+    public CompletableFuture<Boolean> replace(String key, long oldVersion, V newValue) {
+        map.replace(key, newValue);
+        return CompletableFuture.completedFuture(true);
+    }
+
+    @Override
+    public CompletableFuture<Void> addListener(MapEventListener<String, V> listener) {
+        return null;
+    }
+
+    @Override
+    public CompletableFuture<Void> addListener(MapEventListener<String, V> listener, Executor executor) {
+        return null;
+    }
+
+    @Override
+    public CompletableFuture<Void> removeListener(MapEventListener<String, V> listener) {
+        return null;
+    }
+
+    @Override
+    public ConsistentMap<String, V> asConsistentMap() {
+        return null;
+    }
+
+    @Override
+    public ConsistentMap<String, V> asConsistentMap(long timeoutMillis) {
+        return null;
+    }
+
+    @Override
+    public String name() {
+        return null;
+    }
+
+    @Override
+    public ApplicationId applicationId() {
+        return null;
+    }
+
+    @Override
+    public void addStatusChangeListener(Consumer<Status> listener) {
+
+    }
+
+    @Override
+    public void removeStatusChangeListener(Consumer<Status> listener) {
+
+    }
+
+    @Override
+    public Collection<Consumer<Status>> statusChangeListeners() {
+        return null;
+    }
+
+    @Override
+    public CompletableFuture<Version> begin(TransactionId transactionId) {
+        return null;
+    }
+
+    @Override
+    public CompletableFuture<Boolean> prepare(TransactionLog<MapUpdate<String, V>> transactionLog) {
+        return null;
+    }
+
+    @Override
+    public CompletableFuture<Boolean> prepareAndCommit(TransactionLog<MapUpdate<String, V>> transactionLog) {
+        return null;
+    }
+
+    @Override
+    public CompletableFuture<Void> commit(TransactionId transactionId) {
+        return null;
+    }
+
+    @Override
+    public CompletableFuture<Void> rollback(TransactionId transactionId) {
+        return null;
+    }
+}
diff --git a/core/api/src/test/java/org/onosproject/store/primitives/DefaultAtomicCounterMapTest.java b/core/api/src/test/java/org/onosproject/store/primitives/DefaultAtomicCounterMapTest.java
new file mode 100644
index 0000000..55f70a0
--- /dev/null
+++ b/core/api/src/test/java/org/onosproject/store/primitives/DefaultAtomicCounterMapTest.java
@@ -0,0 +1,215 @@
+/*
+ * Copyright 2018-present Open Networking Foundation
+ *
+ * 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.store.primitives;
+
+import org.junit.Before;
+import org.junit.Test;
+import org.onosproject.store.service.ConsistentMapException;
+
+import java.util.concurrent.CompletableFuture;
+
+import static org.hamcrest.MatcherAssert.assertThat;
+import static org.hamcrest.Matchers.is;
+import static org.hamcrest.Matchers.notNullValue;
+import static org.onosproject.store.primitives.TestingCompletableFutures.ErrorState.NONE;
+
+/**
+ * Unit tests for the DefaultAtomicCounter class.
+ */
+
+public class DefaultAtomicCounterMapTest {
+
+    private static final String KEY1 = "myKey1";
+    private static final long VALUE1 = 444L;
+    private static final long DELTA1 = 555L;
+
+    private DefaultAtomicCounterMap<String> atomicCounterMap;
+
+    private DefaultAtomicCounterMap<String> createMap() {
+        AsyncAtomicCounterMapAdapter<String> asyncMap = new AsyncAtomicCounterMapAdapter<>();
+        DefaultAtomicCounterMap<String> map = new DefaultAtomicCounterMap<>(asyncMap, 1000L);
+        assertThat(map, notNullValue());
+        assertThat(map.isEmpty(), is(true));
+        return map;
+    }
+
+    @Before
+    public void setUpMap() {
+        atomicCounterMap = createMap();
+    }
+
+    @Test
+    public void testConstruction() {
+        assertThat(atomicCounterMap.size(), is(0));
+    }
+
+    @Test
+    public void testPutAndGet() {
+        atomicCounterMap.put(KEY1, VALUE1);
+        long value = atomicCounterMap.get(KEY1);
+        assertThat(value, is(VALUE1));
+    }
+
+    @Test
+    public void testGetAndIncrement() {
+        atomicCounterMap.put(KEY1, VALUE1);
+        Long beforeIncrement = atomicCounterMap.getAndIncrement(KEY1);
+        assertThat(beforeIncrement, is(VALUE1));
+        Long afterIncrement = atomicCounterMap.get(KEY1);
+        assertThat(afterIncrement, is(VALUE1 + 1));
+    }
+
+    @Test
+    public void testIncrementAndGet() {
+        atomicCounterMap.put(KEY1, VALUE1);
+        Long afterIncrement = atomicCounterMap.incrementAndGet(KEY1);
+        assertThat(afterIncrement, is(VALUE1 + 1));
+    }
+
+    @Test
+    public void testGetAndDecrement() {
+        atomicCounterMap.put(KEY1, VALUE1);
+        Long beforeDecrement = atomicCounterMap.getAndDecrement(KEY1);
+        assertThat(beforeDecrement, is(VALUE1));
+        Long afterDecrement = atomicCounterMap.get(KEY1);
+        assertThat(afterDecrement, is(VALUE1 - 1));
+    }
+
+    @Test
+    public void testDecrementAndGet() {
+        atomicCounterMap.put(KEY1, VALUE1);
+        Long afterIncrement = atomicCounterMap.decrementAndGet(KEY1);
+        assertThat(afterIncrement, is(VALUE1 - 1));
+    }
+
+    @Test
+    public void testGetAndAdd() {
+        atomicCounterMap.put(KEY1, VALUE1);
+        Long beforeIncrement = atomicCounterMap.getAndAdd(KEY1, DELTA1);
+        assertThat(beforeIncrement, is(VALUE1));
+        Long afterIncrement = atomicCounterMap.get(KEY1);
+        assertThat(afterIncrement, is(VALUE1 + DELTA1));
+    }
+
+    @Test
+    public void testAddAndGet() {
+        atomicCounterMap.put(KEY1, VALUE1);
+        Long afterIncrement = atomicCounterMap.addAndGet(KEY1, DELTA1);
+        assertThat(afterIncrement, is(VALUE1 + DELTA1));
+    }
+
+    @Test
+    public void testPutIfAbsent() {
+        atomicCounterMap.putIfAbsent(KEY1, VALUE1);
+        Long afterIncrement = atomicCounterMap.addAndGet(KEY1, DELTA1);
+        assertThat(afterIncrement, is(VALUE1 + DELTA1));
+    }
+
+    @Test
+    public void testClear() {
+        atomicCounterMap.putIfAbsent(KEY1, VALUE1);
+        assertThat(atomicCounterMap.size(), is(1));
+        atomicCounterMap.clear();
+        assertThat(atomicCounterMap.size(), is(0));
+    }
+
+    @Test
+    public void testReplace() {
+        atomicCounterMap.putIfAbsent(KEY1, VALUE1);
+
+        boolean replaced = atomicCounterMap.replace(KEY1, VALUE1, VALUE1 * 2);
+        assertThat(replaced, is(true));
+        Long afterReplace = atomicCounterMap.get(KEY1);
+        assertThat(afterReplace, is(VALUE1 * 2));
+
+        boolean notReplaced = atomicCounterMap.replace(KEY1, VALUE1, VALUE1 * 2);
+        assertThat(notReplaced, is(false));
+        Long afterNotReplaced = atomicCounterMap.get(KEY1);
+        assertThat(afterNotReplaced, is(VALUE1 * 2));
+    }
+
+    @Test
+    public void testRemove() {
+        atomicCounterMap.putIfAbsent(KEY1, VALUE1);
+        assertThat(atomicCounterMap.size(), is(1));
+        atomicCounterMap.remove(KEY1);
+        assertThat(atomicCounterMap.size(), is(0));
+    }
+
+    @Test
+    public void testRemoveVale() {
+        atomicCounterMap.putIfAbsent(KEY1, VALUE1);
+        assertThat(atomicCounterMap.size(), is(1));
+        atomicCounterMap.remove(KEY1, VALUE1 * 2);
+        assertThat(atomicCounterMap.size(), is(1));
+        atomicCounterMap.remove(KEY1, VALUE1);
+        assertThat(atomicCounterMap.size(), is(0));
+    }
+
+    class AtomicCounterMapWithErrors<K> extends AsyncAtomicCounterMapAdapter<K> {
+
+        TestingCompletableFutures.ErrorState errorState = NONE;
+
+        void setErrorState(TestingCompletableFutures.ErrorState errorState) {
+            this.errorState = errorState;
+        }
+
+        AtomicCounterMapWithErrors() {
+            super();
+        }
+
+        @Override
+        public CompletableFuture<Long> get(K key) {
+            return TestingCompletableFutures.createFuture(errorState);
+        }
+    }
+
+    @Test(expected = ConsistentMapException.Timeout.class)
+    public void testTimeout() {
+        AtomicCounterMapWithErrors<String> atomicCounterMap =
+                new AtomicCounterMapWithErrors<>();
+        atomicCounterMap.setErrorState(TestingCompletableFutures.ErrorState.TIMEOUT_EXCEPTION);
+        DefaultAtomicCounterMap<String> map =
+                new DefaultAtomicCounterMap<>(atomicCounterMap, 1000);
+
+        map.get(KEY1);
+    }
+
+
+    @Test(expected = ConsistentMapException.Interrupted.class)
+    public void testInterrupted() {
+        AtomicCounterMapWithErrors<String> atomicCounterMap =
+                new AtomicCounterMapWithErrors<>();
+        atomicCounterMap.setErrorState(TestingCompletableFutures.ErrorState.INTERRUPTED_EXCEPTION);
+        DefaultAtomicCounterMap<String> map =
+                new DefaultAtomicCounterMap<>(atomicCounterMap, 1000);
+
+        map.get(KEY1);
+    }
+
+    @Test(expected = ConsistentMapException.class)
+    public void testExecutionError() {
+        AtomicCounterMapWithErrors<String> atomicCounterMap =
+                new AtomicCounterMapWithErrors<>();
+        atomicCounterMap.setErrorState(TestingCompletableFutures.ErrorState.EXECUTION_EXCEPTION);
+        DefaultAtomicCounterMap<String> map =
+                new DefaultAtomicCounterMap<>(atomicCounterMap, 1000);
+
+        map.get(KEY1);
+    }
+
+}
\ No newline at end of file
diff --git a/core/api/src/test/java/org/onosproject/store/primitives/DefaultAtomicCounterTest.java b/core/api/src/test/java/org/onosproject/store/primitives/DefaultAtomicCounterTest.java
new file mode 100644
index 0000000..12ab512
--- /dev/null
+++ b/core/api/src/test/java/org/onosproject/store/primitives/DefaultAtomicCounterTest.java
@@ -0,0 +1,141 @@
+/*
+ * Copyright 2018-present Open Networking Foundation
+ *
+ * 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.store.primitives;
+
+import org.junit.Before;
+import org.junit.Test;
+import org.onosproject.store.service.AsyncAtomicCounter;
+import org.onosproject.store.service.StorageException;
+
+import java.util.concurrent.CompletableFuture;
+
+import static org.hamcrest.MatcherAssert.assertThat;
+import static org.hamcrest.Matchers.is;
+import static org.hamcrest.Matchers.notNullValue;
+import static org.onosproject.store.primitives.TestingCompletableFutures.ErrorState.NONE;
+
+
+/**
+ * Unit tests for the DefaultAtomicCounter class.
+ */
+
+public class DefaultAtomicCounterTest {
+
+    private static final long INITIAL_VALUE = 33L;
+    private static final long ADDED_VALUE = 44L;
+
+    private DefaultAtomicCounter atomicCounter;
+
+
+    private DefaultAtomicCounter create() {
+        AsyncAtomicCounter atomicCounter = AsyncAtomicCounterAdapter.builder().build();
+        DefaultAtomicCounter counter = new DefaultAtomicCounter(atomicCounter, 1000);
+        counter.set(INITIAL_VALUE);
+        assertThat(counter.get(), is(INITIAL_VALUE));
+        return counter;
+    }
+
+    @Before
+    public void setUpCounter() {
+        atomicCounter = create();
+    }
+
+    @Test
+    public void testConstruction() {
+        assertThat(atomicCounter, notNullValue());
+    }
+
+    @Test
+    public void testIncrements() {
+        long beforeIncrement = atomicCounter.getAndIncrement();
+        assertThat(beforeIncrement, is(INITIAL_VALUE));
+        assertThat(atomicCounter.get(), is(INITIAL_VALUE + 1));
+
+        atomicCounter.set(INITIAL_VALUE);
+        long afterIncrement = atomicCounter.incrementAndGet();
+        assertThat(afterIncrement, is(INITIAL_VALUE + 1));
+        assertThat(atomicCounter.get(), is(INITIAL_VALUE + 1));
+    }
+
+    @Test
+    public void testAdds() {
+        long beforeIncrement = atomicCounter.getAndAdd(ADDED_VALUE);
+        assertThat(beforeIncrement, is(INITIAL_VALUE));
+        assertThat(atomicCounter.get(), is(INITIAL_VALUE + ADDED_VALUE));
+
+        atomicCounter.set(INITIAL_VALUE);
+        long afterIncrement = atomicCounter.addAndGet(ADDED_VALUE);
+        assertThat(afterIncrement, is(INITIAL_VALUE + ADDED_VALUE));
+        assertThat(atomicCounter.get(), is(INITIAL_VALUE + ADDED_VALUE));
+    }
+
+    @Test
+    public void testCompareAndSet() {
+        boolean compareTrue = atomicCounter.compareAndSet(INITIAL_VALUE, ADDED_VALUE);
+        assertThat(compareTrue, is(true));
+
+        boolean compareFalse = atomicCounter.compareAndSet(INITIAL_VALUE, ADDED_VALUE);
+        assertThat(compareFalse, is(false));
+    }
+
+
+
+    class AtomicCounterWithErrors extends AsyncAtomicCounterAdapter {
+
+        TestingCompletableFutures.ErrorState errorState = NONE;
+
+        void setErrorState(TestingCompletableFutures.ErrorState errorState) {
+            this.errorState = errorState;
+        }
+
+        AtomicCounterWithErrors() {
+            super();
+        }
+
+        @Override
+        public CompletableFuture<Long> get() {
+            return TestingCompletableFutures.createFuture(errorState);
+        }
+    }
+
+    @Test(expected = StorageException.Timeout.class)
+    public void testTimeout() {
+        AtomicCounterWithErrors atomicCounter = new AtomicCounterWithErrors();
+        atomicCounter.setErrorState(TestingCompletableFutures.ErrorState.TIMEOUT_EXCEPTION);
+        DefaultAtomicCounter counter = new DefaultAtomicCounter(atomicCounter, 1000);
+
+        counter.get();
+    }
+
+    @Test(expected = StorageException.Interrupted.class)
+    public void testInterrupted() {
+        AtomicCounterWithErrors atomicCounter = new AtomicCounterWithErrors();
+        atomicCounter.setErrorState(TestingCompletableFutures.ErrorState.INTERRUPTED_EXCEPTION);
+        DefaultAtomicCounter counter = new DefaultAtomicCounter(atomicCounter, 1000);
+
+        counter.get();
+    }
+
+    @Test(expected = StorageException.class)
+    public void testExecutionError() {
+        AtomicCounterWithErrors atomicCounter = new AtomicCounterWithErrors();
+        atomicCounter.setErrorState(TestingCompletableFutures.ErrorState.EXECUTION_EXCEPTION);
+        DefaultAtomicCounter counter = new DefaultAtomicCounter(atomicCounter, 1000);
+
+        counter.get();
+    }
+}
\ No newline at end of file
diff --git a/core/api/src/test/java/org/onosproject/store/primitives/DefaultConsistentTreeMapTest.java b/core/api/src/test/java/org/onosproject/store/primitives/DefaultConsistentTreeMapTest.java
new file mode 100644
index 0000000..8bfc820
--- /dev/null
+++ b/core/api/src/test/java/org/onosproject/store/primitives/DefaultConsistentTreeMapTest.java
@@ -0,0 +1,320 @@
+/*
+ * Copyright 2018-present Open Networking Foundation
+ *
+ * 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.store.primitives;
+
+import org.hamcrest.Description;
+import org.hamcrest.TypeSafeMatcher;
+import org.junit.Before;
+import org.junit.Test;
+import org.onosproject.store.service.ConsistentMapException;
+import org.onosproject.store.service.MapEvent;
+import org.onosproject.store.service.MapEventListener;
+import org.onosproject.store.service.Versioned;
+
+import java.util.LinkedList;
+import java.util.Map;
+import java.util.Objects;
+import java.util.Set;
+import java.util.concurrent.CompletableFuture;
+import java.util.concurrent.Executor;
+import java.util.stream.Collectors;
+
+import static org.hamcrest.MatcherAssert.assertThat;
+import static org.hamcrest.Matchers.hasItems;
+import static org.hamcrest.Matchers.hasSize;
+import static org.hamcrest.Matchers.is;
+import static org.hamcrest.Matchers.notNullValue;
+import static org.onosproject.store.primitives.TestingCompletableFutures.ErrorState.NONE;
+
+public class DefaultConsistentTreeMapTest {
+
+    private static final String MIN_KEY = "0";
+    private static final String KEY1 = "A";
+    private static final String VALUE1 = "A";
+    private static final String KEY2 = "B";
+    private static final String VALUE2 = "B";
+    private static final String KEY3 = "C";
+    private static final String VALUE3 = "C";
+    private static final String KEY4 = "D";
+    private static final String VALUE4 = "D";
+    private static final String KEY5 = "E";
+    private static final String VALUE5 = "E";
+    private static final String MAX_KEY = "Z";
+    private static final String NO_SUCH_VALUE = "BAD VALUE";
+    private static final String NO_SUCH_KEY = "BAD KEY";
+    private static final String DEFAULT_VALUE = "DEFAULT";
+
+    private DefaultConsistentTreeMap<String> treeMap;
+    private TestAsyncConsistentTreeMap<String> asyncMap;
+
+    private static class TestAsyncConsistentTreeMap<V> extends AsyncConsistentTreeMapAdapter<V> {
+        LinkedList<MapEventListener<String, V>> listeners = new LinkedList<>();
+
+        @Override
+        public CompletableFuture<Void> addListener(MapEventListener<String, V> listener,
+                                                   Executor executor) {
+            listeners.add(listener);
+            return CompletableFuture.completedFuture(null);
+        }
+
+        @Override
+        public CompletableFuture<Void> removeListener(MapEventListener<String, V> listener) {
+            listeners.remove(listener);
+            return CompletableFuture.completedFuture(null);
+        }
+    }
+
+    class Listener implements MapEventListener<String, String> {
+        @Override
+        public void event(MapEvent<String, String> event) {
+            // Nothing to do here
+        }
+    }
+
+    private DefaultConsistentTreeMap<String> createMap() {
+        asyncMap = new TestAsyncConsistentTreeMap<>();
+        DefaultConsistentTreeMap<String> map = new DefaultConsistentTreeMap<>(asyncMap, 1000L);
+        assertThat(map, notNullValue());
+        assertThat(map.isEmpty(), is(true));
+        map.putIfAbsent(KEY1, VALUE1);
+        map.putIfAbsent(KEY2, VALUE2);
+        map.putIfAbsent(KEY3, VALUE3);
+        return map;
+    }
+
+    static class VersionedMatcher extends TypeSafeMatcher<Versioned<String>> {
+        String expectedValue;
+
+        VersionedMatcher(String expectedValue) {
+            this.expectedValue = expectedValue;
+        }
+
+        @Override
+        public boolean matchesSafely(Versioned<String> value) {
+            return expectedValue.equals(value.value());
+        }
+
+        @Override
+        public void describeTo(Description description) {
+            description.appendText("<Versioned{value=" + expectedValue + ",...");
+        }
+    }
+
+    private static VersionedMatcher matchesVersioned(String expectedValue) {
+        return new VersionedMatcher(expectedValue);
+    }
+
+    @Before
+    public void setUpMap() {
+        treeMap = createMap();
+    }
+
+    @Test
+    public void testKeys() {
+        assertThat(treeMap.size(), is(3));
+        assertThat(treeMap.navigableKeySet(), hasSize(3));
+
+        assertThat(treeMap.firstKey(), is(VALUE1));
+        assertThat(treeMap.lastKey(), is(VALUE3));
+        assertThat(treeMap.lowerKey(KEY2), is(VALUE1));
+        assertThat(treeMap.higherKey(KEY2), is(VALUE3));
+        assertThat(treeMap.floorKey(MAX_KEY), is(VALUE3));
+        assertThat(treeMap.ceilingKey(MIN_KEY), is(VALUE1));
+
+        assertThat(treeMap.containsKey(KEY2), is(true));
+        assertThat(treeMap.containsKey(MAX_KEY), is(false));
+    }
+
+    private void checkEntry(Map.Entry<String, Versioned<String>> entry,
+                            String expectedKey,
+                            String expectedValue) {
+        assertThat(entry.getKey(), is(expectedKey));
+        assertThat(entry.getValue(), matchesVersioned(expectedValue));
+    }
+
+    @Test
+    public void testEntries() {
+        assertThat(treeMap.size(), is(3));
+
+        checkEntry(treeMap.firstEntry(), KEY1, VALUE1);
+        checkEntry(treeMap.lastEntry(), KEY3, VALUE3);
+        checkEntry(treeMap.lowerEntry(KEY2), KEY1, VALUE1);
+        checkEntry(treeMap.higherEntry(KEY2), KEY3, VALUE3);
+        checkEntry(treeMap.floorEntry(MAX_KEY), KEY3, VALUE3);
+        checkEntry(treeMap.ceilingEntry(MIN_KEY), KEY1, VALUE1);
+
+        checkEntry(treeMap.pollFirstEntry(), KEY1, VALUE1);
+        assertThat(treeMap.size(), is(2));
+
+        checkEntry(treeMap.pollLastEntry(), KEY3, VALUE3);
+        assertThat(treeMap.size(), is(1));
+    }
+
+    @Test
+    public void testGets() {
+        assertThat(treeMap.get(KEY2), matchesVersioned(VALUE2));
+        assertThat(treeMap.containsValue(VALUE3), is(true));
+        assertThat(treeMap.getOrDefault(KEY3, DEFAULT_VALUE), matchesVersioned(VALUE3));
+        assertThat(treeMap.getOrDefault(NO_SUCH_KEY, DEFAULT_VALUE), matchesVersioned(DEFAULT_VALUE));
+        assertThat(treeMap.compute(KEY4, (k, v) -> v == null ? VALUE4 : ""), matchesVersioned(VALUE4));
+        assertThat(treeMap.computeIf(KEY4, Objects::isNull, (k, v) -> NO_SUCH_VALUE), matchesVersioned(VALUE4));
+        assertThat(treeMap.computeIfPresent(KEY4, (k, v) -> NO_SUCH_VALUE), matchesVersioned(NO_SUCH_VALUE));
+        assertThat(treeMap.computeIfAbsent(KEY2, (v) -> NO_SUCH_VALUE), matchesVersioned(VALUE2));
+        treeMap.put(KEY5, VALUE5);
+        assertThat(treeMap.putAndGet(KEY5, VALUE1), matchesVersioned(VALUE5));
+        assertThat(treeMap.get(KEY5), matchesVersioned(VALUE1));
+    }
+
+    @Test
+    public void testSets() {
+        Set<String> keys = treeMap.keySet();
+        assertThat(keys, hasSize(3));
+        assertThat(keys, hasItems(KEY1, KEY2, KEY3));
+
+        Set<String> values = treeMap.values().stream().map(Versioned::value).collect(Collectors.toSet());
+        assertThat(values, hasSize(3));
+        assertThat(values, hasItems(VALUE1, VALUE2, VALUE3));
+
+        Set<String> valuesFromEntries = treeMap.entrySet().stream()
+                .map(entry -> entry.getValue().value()).collect(Collectors.toSet());
+        assertThat(valuesFromEntries, hasSize(3));
+        assertThat(valuesFromEntries, hasItems(VALUE1, VALUE2, VALUE3));
+
+        Set<String> keysFromEntries = treeMap.entrySet().stream()
+                .map(Map.Entry::getKey).collect(Collectors.toSet());
+        assertThat(keysFromEntries, hasSize(3));
+        assertThat(keysFromEntries, hasItems(KEY1, KEY2, KEY3));
+    }
+
+    @Test
+    public void testRemoves() {
+        treeMap.remove(KEY1);
+        assertThat(treeMap.size(), is(2));
+
+        treeMap.remove(KEY2, 1L);
+        assertThat(treeMap.size(), is(1));
+
+        treeMap.remove(KEY3, VALUE3);
+        assertThat(treeMap.size(), is(0));
+    }
+
+    @Test
+    public void testClear() {
+        treeMap.clear();
+        assertThat(treeMap.size(), is(0));
+    }
+
+    @Test
+    public void testReplaces() {
+        treeMap.replace(KEY1, VALUE2);
+        assertThat(treeMap.get(KEY1), matchesVersioned(VALUE2));
+
+        treeMap.replace(KEY2, 1L, VALUE1);
+        assertThat(treeMap.get(KEY2), matchesVersioned(VALUE1));
+
+        treeMap.replace(KEY3, VALUE3, VALUE5);
+        assertThat(treeMap.get(KEY3), matchesVersioned(VALUE5));
+    }
+
+    @Test
+    public void testJavaMap() {
+        Map<String, String> javaMap = treeMap.asJavaMap();
+        assertThat(javaMap.entrySet(), hasSize(3));
+        assertThat(javaMap.values(), hasItems(VALUE1, VALUE2, VALUE3));
+        assertThat(javaMap.keySet(), hasItems(KEY1, KEY2, KEY3));
+    }
+
+    @Test
+    public void testSubMap() {
+        treeMap.putIfAbsent(KEY4, VALUE4);
+        treeMap.putIfAbsent(KEY5, VALUE5);
+
+        Map<String, String> subMap = treeMap.subMap(KEY2, KEY4, true, true);
+        assertThat(subMap.entrySet(), hasSize(3));
+        assertThat(subMap.values(), hasItems(VALUE2, VALUE3, VALUE4));
+        assertThat(subMap.keySet(), hasItems(KEY2, KEY3, KEY4));
+    }
+
+    @Test
+    public void testListeners() {
+        Listener listener1 = new Listener();
+        Listener listener2 = new Listener();
+
+        assertThat(asyncMap.listeners, hasSize(0));
+        treeMap.addListener(listener1);
+        assertThat(asyncMap.listeners, hasSize(1));
+        treeMap.addListener(listener2);
+        assertThat(asyncMap.listeners, hasSize(2));
+
+        treeMap.removeListener(listener1);
+        treeMap.removeListener(listener2);
+        assertThat(asyncMap.listeners, hasSize(0));
+    }
+
+    class ConsistentTreeMapWithError<K> extends AsyncConsistentTreeMapAdapter<K> {
+
+        TestingCompletableFutures.ErrorState errorState = NONE;
+
+        void setErrorState(TestingCompletableFutures.ErrorState errorState) {
+            this.errorState = errorState;
+        }
+
+        ConsistentTreeMapWithError() {
+            super();
+        }
+
+        @Override
+        public CompletableFuture<String> lowerKey(String key) {
+            return TestingCompletableFutures.createStringFuture(errorState);
+        }
+    }
+
+    @Test(expected = ConsistentMapException.Timeout.class)
+    public void testTimeout() {
+        ConsistentTreeMapWithError<String> consistentMap =
+                new ConsistentTreeMapWithError<>();
+        consistentMap.setErrorState(TestingCompletableFutures.ErrorState.TIMEOUT_EXCEPTION);
+        DefaultConsistentTreeMap<String> map =
+                new DefaultConsistentTreeMap<>(consistentMap, 1000);
+
+        map.lowerKey(KEY1);
+    }
+
+
+    @Test(expected = ConsistentMapException.Interrupted.class)
+    public void testInterrupted() {
+        ConsistentTreeMapWithError<String> consistentMap =
+                new ConsistentTreeMapWithError<>();
+        consistentMap.setErrorState(TestingCompletableFutures.ErrorState.INTERRUPTED_EXCEPTION);
+        DefaultConsistentTreeMap<String> map =
+                new DefaultConsistentTreeMap<>(consistentMap, 1000);
+
+        map.lowerKey(KEY1);
+    }
+
+    @Test(expected = ConsistentMapException.class)
+    public void testExecutionError() {
+        ConsistentTreeMapWithError<String> consistentMap =
+                new ConsistentTreeMapWithError<>();
+        consistentMap.setErrorState(TestingCompletableFutures.ErrorState.EXECUTION_EXCEPTION);
+        DefaultConsistentTreeMap<String> map =
+                new DefaultConsistentTreeMap<>(consistentMap, 1000);
+
+        map.lowerKey(KEY1);
+    }
+
+}
\ No newline at end of file
diff --git a/core/api/src/test/java/org/onosproject/store/primitives/TestingCompletableFutures.java b/core/api/src/test/java/org/onosproject/store/primitives/TestingCompletableFutures.java
new file mode 100644
index 0000000..0b5c0b5
--- /dev/null
+++ b/core/api/src/test/java/org/onosproject/store/primitives/TestingCompletableFutures.java
@@ -0,0 +1,96 @@
+/*
+ * Copyright 2018-present Open Networking Foundation
+ *
+ * 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.store.primitives;
+
+import java.util.concurrent.CompletableFuture;
+import java.util.concurrent.ExecutionException;
+import java.util.concurrent.TimeUnit;
+import java.util.concurrent.TimeoutException;
+
+/**
+ * Completable Futures with known error states used for testing.
+ */
+public final class TestingCompletableFutures {
+
+    private TestingCompletableFutures() {
+    }
+
+    /** Indicates which kind of error to produce. */
+    public enum ErrorState { NONE, INTERRUPTED_EXCEPTION, TIMEOUT_EXCEPTION, EXECUTION_EXCEPTION }
+
+    private static class TimeoutExceptionFuture<T> extends CompletableFuture<T> {
+        @Override
+        public T get(long timeout, TimeUnit unit)
+                throws TimeoutException {
+            throw new TimeoutException();
+        }
+    }
+
+    private static class InterruptedFuture<T> extends CompletableFuture<T> {
+        @Override
+        public T get(long timeout, TimeUnit unit)
+                throws InterruptedException {
+            throw new InterruptedException();
+        }
+    }
+
+    private static class ExecutionExceptionFuture<T> extends CompletableFuture<T> {
+        @Override
+        public T get(long timeout, TimeUnit unit)
+                throws ExecutionException {
+            throw new ExecutionException("", new Exception());
+        }
+    }
+
+    /**
+     * Creates a Long Future for a given error type.
+     *
+     * @param errorState wht kind of error to produce
+     * @return new future that will generate the requested error
+     */
+    public static CompletableFuture<Long> createFuture(ErrorState errorState) {
+        switch (errorState) {
+            case TIMEOUT_EXCEPTION:
+                return new TimeoutExceptionFuture<>();
+            case INTERRUPTED_EXCEPTION:
+                return new InterruptedFuture<>();
+            case EXECUTION_EXCEPTION:
+                return new ExecutionExceptionFuture<>();
+            default:
+                return new CompletableFuture<>();
+        }
+    }
+
+    /**
+     * Creates a Long Future for a given error type.
+     *
+     * @param errorState wht kind of error to produce
+     * @return new future that will generate the requested error
+     */
+    public static CompletableFuture<String> createStringFuture(ErrorState errorState) {
+        switch (errorState) {
+            case TIMEOUT_EXCEPTION:
+                return new TimeoutExceptionFuture<>();
+            case INTERRUPTED_EXCEPTION:
+                return new InterruptedFuture<>();
+            case EXECUTION_EXCEPTION:
+                return new ExecutionExceptionFuture<>();
+            default:
+                return new CompletableFuture<>();
+        }
+    }
+}
diff --git a/core/api/src/test/java/org/onosproject/store/service/TestStorageService.java b/core/api/src/test/java/org/onosproject/store/service/TestStorageService.java
index e41d2ad..48ffeac 100644
--- a/core/api/src/test/java/org/onosproject/store/service/TestStorageService.java
+++ b/core/api/src/test/java/org/onosproject/store/service/TestStorageService.java
@@ -15,6 +15,8 @@
  */
 package org.onosproject.store.service;
 
+import org.onosproject.store.primitives.AsyncAtomicCounterAdapter;
+
 public class TestStorageService extends StorageServiceAdapter {
 
 
@@ -35,7 +37,7 @@
 
     @Override
     public AtomicCounterBuilder atomicCounterBuilder() {
-        return TestAtomicCounter.builder();
+        return AsyncAtomicCounterAdapter.builder();
     }
 
     @Override
