Aaron Kruglikov
Committed by Gerrit Code Review

Adding additional resources for instantiating async consistent treemaps.

Change-Id: I7bfc602ac22eda1844fea2a7b3e3133f83157bf3
...@@ -16,6 +16,7 @@ ...@@ -16,6 +16,7 @@
16 package org.onosproject.vtnrsc.util; 16 package org.onosproject.vtnrsc.util;
17 17
18 import org.onosproject.store.service.Topic; 18 import org.onosproject.store.service.Topic;
19 +import org.onosproject.store.service.ConsistentTreeMapBuilder;
19 import org.onosproject.store.service.WorkQueue; 20 import org.onosproject.store.service.WorkQueue;
20 import org.onosproject.store.service.EventuallyConsistentMapBuilder; 21 import org.onosproject.store.service.EventuallyConsistentMapBuilder;
21 import org.onosproject.store.service.ConsistentMapBuilder; 22 import org.onosproject.store.service.ConsistentMapBuilder;
...@@ -42,6 +43,11 @@ public class VtnStorageServiceAdapter implements StorageService { ...@@ -42,6 +43,11 @@ public class VtnStorageServiceAdapter implements StorageService {
42 } 43 }
43 44
44 @Override 45 @Override
46 + public <V> ConsistentTreeMapBuilder<V> consistentTreeMapBuilder() {
47 + return null;
48 + }
49 +
50 + @Override
45 public <E> DistributedSetBuilder<E> setBuilder() { 51 public <E> DistributedSetBuilder<E> setBuilder() {
46 return null; 52 return null;
47 } 53 }
......
...@@ -45,7 +45,6 @@ import java.util.function.Predicate; ...@@ -45,7 +45,6 @@ import java.util.function.Predicate;
45 public class DefaultConsistentTreeMap<V> 45 public class DefaultConsistentTreeMap<V>
46 extends Synchronous<AsyncConsistentTreeMap<V>> 46 extends Synchronous<AsyncConsistentTreeMap<V>>
47 implements ConsistentTreeMap<V> { 47 implements ConsistentTreeMap<V> {
48 - private static final int MAX_DELAY_BETWEEN_RETRY_MILLIS = 50;
49 private final AsyncConsistentTreeMap<V> treeMap; 48 private final AsyncConsistentTreeMap<V> treeMap;
50 private final long operationTimeoutMillis; 49 private final long operationTimeoutMillis;
51 private Map<String, V> javaMap; 50 private Map<String, V> javaMap;
......
...@@ -20,6 +20,7 @@ import java.util.Set; ...@@ -20,6 +20,7 @@ import java.util.Set;
20 import org.onosproject.store.service.AsyncAtomicCounter; 20 import org.onosproject.store.service.AsyncAtomicCounter;
21 import org.onosproject.store.service.AsyncAtomicValue; 21 import org.onosproject.store.service.AsyncAtomicValue;
22 import org.onosproject.store.service.AsyncConsistentMap; 22 import org.onosproject.store.service.AsyncConsistentMap;
23 +import org.onosproject.store.service.AsyncConsistentTreeMap;
23 import org.onosproject.store.service.AsyncDistributedSet; 24 import org.onosproject.store.service.AsyncDistributedSet;
24 import org.onosproject.store.service.AsyncLeaderElector; 25 import org.onosproject.store.service.AsyncLeaderElector;
25 import org.onosproject.store.service.WorkQueue; 26 import org.onosproject.store.service.WorkQueue;
...@@ -42,6 +43,16 @@ public interface DistributedPrimitiveCreator { ...@@ -42,6 +43,16 @@ public interface DistributedPrimitiveCreator {
42 <K, V> AsyncConsistentMap<K, V> newAsyncConsistentMap(String name, Serializer serializer); 43 <K, V> AsyncConsistentMap<K, V> newAsyncConsistentMap(String name, Serializer serializer);
43 44
44 /** 45 /**
46 + * Creates a new {@code AsyncConsistentTreeMap}.
47 + *
48 + * @param name tree name
49 + * @param serializer serializer to use for serializing/deserializing map entries
50 + * @param <V> value type
51 + * @return distributedTreeMap
52 + */
53 + <V> AsyncConsistentTreeMap<V> newAsyncConsistentTreeMap(String name, Serializer serializer);
54 +
55 + /**
45 * Creates a new {@code AsyncAtomicCounter}. 56 * Creates a new {@code AsyncAtomicCounter}.
46 * 57 *
47 * @param name counter name 58 * @param name counter name
......
1 +/*
2 + * Copyright 2016-present 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 +package org.onosproject.store.service;
18 +
19 +import org.onosproject.store.primitives.DistributedPrimitiveBuilder;
20 +
21 +/**
22 + * Builder for {@link ConsistentTreeMap}.
23 + */
24 +public abstract class ConsistentTreeMapBuilder<V>
25 + extends DistributedPrimitiveBuilder<ConsistentTreeMapBuilder<V>, ConsistentTreeMap<V>> {
26 +
27 + private boolean purgeOnUninstall = false;
28 +
29 + public ConsistentTreeMapBuilder() {
30 + super(DistributedPrimitive.Type.CONSISTENT_TREEMAP);
31 + }
32 +
33 + /**
34 + * Clears map contents when the owning application is uninstalled.
35 + *
36 + * @return this builder
37 + */
38 + public ConsistentTreeMapBuilder<V> withPurgeOnUninstall() {
39 + purgeOnUninstall = true;
40 + return this;
41 + }
42 +
43 + /**
44 + * Return if map entries need to be cleared when owning application is uninstalled.
45 + *
46 + * @return true if items are to be cleared on uninstall
47 + */
48 + public boolean purgeOnUninstall() {
49 + return purgeOnUninstall;
50 + }
51 +
52 + /**
53 + * Builds the distributed tree map based on the configuration options supplied
54 + * to this builder.
55 + *
56 + * @return new distributed tree map
57 + * @throw java.lang.RuntimeException if a mandatory parameter is missing
58 + */
59 + public abstract AsyncConsistentTreeMap<V> buildTreeMap();
60 +
61 +}
...@@ -52,6 +52,11 @@ public interface DistributedPrimitive { ...@@ -52,6 +52,11 @@ public interface DistributedPrimitive {
52 SET, 52 SET,
53 53
54 /** 54 /**
55 + * Tree map.
56 + */
57 + CONSISTENT_TREEMAP,
58 +
59 + /**
55 * atomic counter. 60 * atomic counter.
56 */ 61 */
57 COUNTER, 62 COUNTER,
......
...@@ -44,6 +44,14 @@ public interface StorageService { ...@@ -44,6 +44,14 @@ public interface StorageService {
44 <K, V> ConsistentMapBuilder<K, V> consistentMapBuilder(); 44 <K, V> ConsistentMapBuilder<K, V> consistentMapBuilder();
45 45
46 /** 46 /**
47 + * Creates a new {@code AsyncConsistentTreeMapBuilder}.
48 + *
49 + * @param <V> value type
50 + * @return builder for a async consistent tree map
51 + */
52 + <V> ConsistentTreeMapBuilder<V> consistentTreeMapBuilder();
53 +
54 + /**
47 * Creates a new DistributedSetBuilder. 55 * Creates a new DistributedSetBuilder.
48 * 56 *
49 * @param <E> set element type 57 * @param <E> set element type
......
...@@ -63,4 +63,8 @@ public class StorageServiceAdapter implements StorageService { ...@@ -63,4 +63,8 @@ public class StorageServiceAdapter implements StorageService {
63 public <T> Topic<T> getTopic(String name, Serializer serializer) { 63 public <T> Topic<T> getTopic(String name, Serializer serializer) {
64 return null; 64 return null;
65 } 65 }
66 +
67 + public <V> ConsistentTreeMapBuilder<V> consistentTreeMapBuilder() {
68 + return null;
69 + }
66 } 70 }
......
...@@ -31,6 +31,7 @@ import org.onosproject.store.primitives.MapUpdate; ...@@ -31,6 +31,7 @@ import org.onosproject.store.primitives.MapUpdate;
31 import org.onosproject.store.primitives.TransactionId; 31 import org.onosproject.store.primitives.TransactionId;
32 import org.onosproject.store.primitives.resources.impl.AtomixConsistentMapCommands; 32 import org.onosproject.store.primitives.resources.impl.AtomixConsistentMapCommands;
33 import org.onosproject.store.primitives.resources.impl.AtomixConsistentMapFactory; 33 import org.onosproject.store.primitives.resources.impl.AtomixConsistentMapFactory;
34 +import org.onosproject.store.primitives.resources.impl.AtomixConsistentTreeMapCommands;
34 import org.onosproject.store.primitives.resources.impl.AtomixLeaderElectorCommands; 35 import org.onosproject.store.primitives.resources.impl.AtomixLeaderElectorCommands;
35 import org.onosproject.store.primitives.resources.impl.AtomixLeaderElectorFactory; 36 import org.onosproject.store.primitives.resources.impl.AtomixLeaderElectorFactory;
36 import org.onosproject.store.primitives.resources.impl.AtomixWorkQueueCommands; 37 import org.onosproject.store.primitives.resources.impl.AtomixWorkQueueCommands;
...@@ -96,6 +97,7 @@ public final class CatalystSerializers { ...@@ -96,6 +97,7 @@ public final class CatalystSerializers {
96 serializer.resolve(new AtomixLeaderElectorCommands.TypeResolver()); 97 serializer.resolve(new AtomixLeaderElectorCommands.TypeResolver());
97 serializer.resolve(new AtomixWorkQueueCommands.TypeResolver()); 98 serializer.resolve(new AtomixWorkQueueCommands.TypeResolver());
98 serializer.resolve(new ResourceManagerTypeResolver()); 99 serializer.resolve(new ResourceManagerTypeResolver());
100 + serializer.resolve(new AtomixConsistentTreeMapCommands.TypeResolver());
99 101
100 serializer.registerClassLoader(AtomixConsistentMapFactory.class) 102 serializer.registerClassLoader(AtomixConsistentMapFactory.class)
101 .registerClassLoader(AtomixLeaderElectorFactory.class) 103 .registerClassLoader(AtomixLeaderElectorFactory.class)
......
1 +/*
2 + * Copyright 2016-present 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.store.primitives.impl;
17 +
18 +import org.onosproject.store.primitives.DistributedPrimitiveCreator;
19 +import org.onosproject.store.service.AsyncConsistentTreeMap;
20 +import org.onosproject.store.service.ConsistentTreeMap;
21 +import org.onosproject.store.service.ConsistentTreeMapBuilder;
22 +
23 +/**
24 + * Default {@link org.onosproject.store.service.AsyncConsistentTreeMap} builder.
25 + *
26 + * @param <V> type for map value
27 + */
28 +public class DefaultConsistentTreeMapBuilder<V> extends ConsistentTreeMapBuilder<V> {
29 +
30 + private final DistributedPrimitiveCreator primitiveCreator;
31 +
32 + public DefaultConsistentTreeMapBuilder(DistributedPrimitiveCreator primitiveCreator) {
33 + this.primitiveCreator = primitiveCreator;
34 + }
35 +
36 + @Override
37 + public AsyncConsistentTreeMap<V> buildTreeMap() {
38 + return primitiveCreator.newAsyncConsistentTreeMap(name(), serializer());
39 + }
40 +
41 + @Override
42 + public ConsistentTreeMap<V> build() {
43 + return buildTreeMap().asTreeMap();
44 + }
45 +
46 +}
1 +/*
2 + * Copyright 2016-present 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 +package org.onosproject.store.primitives.impl;
18 +
19 +import org.onosproject.store.primitives.TransactionId;
20 +import org.onosproject.store.service.AsyncConsistentTreeMap;
21 +import org.onosproject.store.service.MapEventListener;
22 +import org.onosproject.store.service.MapTransaction;
23 +import org.onosproject.store.service.Versioned;
24 +
25 +import java.util.Collection;
26 +import java.util.Map;
27 +import java.util.NavigableMap;
28 +import java.util.NavigableSet;
29 +import java.util.Objects;
30 +import java.util.Set;
31 +import java.util.concurrent.CompletableFuture;
32 +import java.util.concurrent.Executor;
33 +import java.util.function.BiFunction;
34 +import java.util.function.Predicate;
35 +
36 +import static com.google.common.base.Preconditions.checkNotNull;
37 +
38 +/**
39 + * A {@link AsyncConsistentTreeMap} that delegates control to another instance
40 + * of {@link AsyncConsistentTreeMap}.
41 + */
42 +public class DelegatingAsyncConsistentTreeMap<V>
43 + implements AsyncConsistentTreeMap<V> {
44 +
45 + private final AsyncConsistentTreeMap<V> delegateMap;
46 +
47 + DelegatingAsyncConsistentTreeMap(AsyncConsistentTreeMap<V> delegateMap) {
48 + this.delegateMap = checkNotNull(delegateMap,
49 + "delegate map cannot be null");
50 + }
51 +
52 + @Override
53 + public CompletableFuture<String> firstKey() {
54 + return delegateMap.firstKey();
55 + }
56 +
57 + @Override
58 + public CompletableFuture<String> lastKey() {
59 + return delegateMap.lastKey();
60 + }
61 +
62 + @Override
63 + public CompletableFuture<Map.Entry<String, Versioned<V>>> ceilingEntry(String key) {
64 + return delegateMap.ceilingEntry(key);
65 + }
66 +
67 + @Override
68 + public CompletableFuture<Map.Entry<String, Versioned<V>>> floorEntry(String key) {
69 + return delegateMap.floorEntry(key);
70 + }
71 +
72 + @Override
73 + public CompletableFuture<Map.Entry<String, Versioned<V>>> higherEntry(String key) {
74 + return delegateMap.higherEntry(key);
75 + }
76 +
77 + @Override
78 + public CompletableFuture<Map.Entry<String, Versioned<V>>> lowerEntry(String key) {
79 + return delegateMap.lowerEntry(key);
80 + }
81 +
82 + @Override
83 + public CompletableFuture<Map.Entry<String, Versioned<V>>> firstEntry() {
84 + return delegateMap.firstEntry();
85 + }
86 +
87 + @Override
88 + public CompletableFuture<Map.Entry<String, Versioned<V>>> lastEntry() {
89 + return delegateMap.lastEntry();
90 + }
91 +
92 + @Override
93 + public CompletableFuture<Map.Entry<String, Versioned<V>>> pollFirstEntry() {
94 + return delegateMap.pollFirstEntry();
95 + }
96 +
97 + @Override
98 + public CompletableFuture<Map.Entry<String, Versioned<V>>> pollLastEntry() {
99 + return delegateMap.pollLastEntry();
100 + }
101 +
102 + @Override
103 + public CompletableFuture<String> lowerKey(String key) {
104 + return delegateMap.lowerKey(key);
105 + }
106 +
107 + @Override
108 + public CompletableFuture<String> floorKey(String key) {
109 + return delegateMap.floorKey(key);
110 + }
111 +
112 + @Override
113 + public CompletableFuture<String> ceilingKey(String key) {
114 + return delegateMap.ceilingKey(key);
115 + }
116 +
117 + @Override
118 + public CompletableFuture<String> higherKey(String key) {
119 + return delegateMap.higherKey(key);
120 + }
121 +
122 + @Override
123 + public CompletableFuture<NavigableSet<String>> navigableKeySet() {
124 + return delegateMap.navigableKeySet();
125 + }
126 +
127 + @Override
128 + public CompletableFuture<NavigableMap<String, V>> subMap(
129 + String upperKey,
130 + String lowerKey,
131 + boolean inclusiveUpper,
132 + boolean inclusiveLower) {
133 + return delegateMap.subMap(upperKey, lowerKey,
134 + inclusiveUpper, inclusiveLower);
135 + }
136 +
137 + @Override
138 + public String name() {
139 + return delegateMap.name();
140 + }
141 +
142 + @Override
143 + public CompletableFuture<Integer> size() {
144 + return delegateMap.size();
145 + }
146 +
147 + @Override
148 + public CompletableFuture<Boolean> containsKey(String key) {
149 + return delegateMap.containsKey(key);
150 + }
151 +
152 + @Override
153 + public CompletableFuture<Boolean> containsValue(V value) {
154 + return delegateMap.containsValue(value);
155 + }
156 +
157 + @Override
158 + public CompletableFuture<Versioned<V>> get(String key) {
159 + return delegateMap.get(key);
160 + }
161 +
162 + @Override
163 + public CompletableFuture<Versioned<V>> computeIf(
164 + String key,
165 + Predicate<? super V> condition,
166 + BiFunction<? super String, ? super V,
167 + ? extends V> remappingFunction) {
168 + return delegateMap.computeIf(key, condition, remappingFunction);
169 + }
170 +
171 + @Override
172 + public CompletableFuture<Versioned<V>> put(String key, V value) {
173 + return delegateMap.put(key, value);
174 + }
175 +
176 + @Override
177 + public CompletableFuture<Versioned<V>> putAndGet(String key, V value) {
178 + return delegateMap.putAndGet(key, value);
179 + }
180 +
181 + @Override
182 + public CompletableFuture<Versioned<V>> remove(String key) {
183 + return delegateMap.remove(key);
184 + }
185 +
186 + @Override
187 + public CompletableFuture<Void> clear() {
188 + return delegateMap.clear();
189 + }
190 +
191 + @Override
192 + public CompletableFuture<Set<String>> keySet() {
193 + return delegateMap.keySet();
194 + }
195 +
196 + @Override
197 + public CompletableFuture<Collection<Versioned<V>>> values() {
198 + return delegateMap.values();
199 + }
200 +
201 + @Override
202 + public CompletableFuture<Set<Map.Entry<String, Versioned<V>>>> entrySet() {
203 + return delegateMap.entrySet();
204 + }
205 +
206 + @Override
207 + public CompletableFuture<Versioned<V>> putIfAbsent(String key, V value) {
208 + return delegateMap.putIfAbsent(key, value);
209 + }
210 +
211 + @Override
212 + public CompletableFuture<Boolean> remove(String key, V value) {
213 + return delegateMap.remove(key, value);
214 + }
215 +
216 + @Override
217 + public CompletableFuture<Boolean> remove(String key, long version) {
218 + return delegateMap.remove(key, version);
219 + }
220 +
221 + @Override
222 + public CompletableFuture<Versioned<V>> replace(String key, V value) {
223 + return delegateMap.replace(key, value);
224 + }
225 +
226 + @Override
227 + public CompletableFuture<Boolean> replace(String key, V oldValue,
228 + V newValue) {
229 + return delegateMap.replace(key, oldValue, newValue);
230 + }
231 +
232 + @Override
233 + public CompletableFuture<Boolean> replace(String key, long oldVersion,
234 + V newValue) {
235 + return delegateMap.replace(key, oldVersion, newValue);
236 + }
237 +
238 + @Override
239 + public CompletableFuture<Void> addListener(
240 + MapEventListener<String, V> listener, Executor executor) {
241 + return delegateMap.addListener(listener, executor);
242 + }
243 +
244 + @Override
245 + public CompletableFuture<Void> removeListener(
246 + MapEventListener<String, V> listener) {
247 + return delegateMap.removeListener(listener);
248 + }
249 +
250 + @Override
251 + public CompletableFuture<Boolean> prepare(
252 + MapTransaction<String, V> transaction) {
253 + return delegateMap.prepare(transaction);
254 + }
255 +
256 + @Override
257 + public CompletableFuture<Void> commit(TransactionId transactionId) {
258 + return delegateMap.commit(transactionId);
259 + }
260 +
261 + @Override
262 + public CompletableFuture<Void> rollback(TransactionId transactionId) {
263 + return delegateMap.rollback(transactionId);
264 + }
265 +
266 + @Override
267 + public CompletableFuture<Boolean> prepareAndCommit(
268 + MapTransaction<String, V> transaction) {
269 + return delegateMap.prepareAndCommit(transaction);
270 + }
271 +
272 + @Override
273 + public boolean equals(Object other) {
274 + if (other instanceof DelegatingAsyncConsistentTreeMap) {
275 + DelegatingAsyncConsistentTreeMap<V> that =
276 + (DelegatingAsyncConsistentTreeMap) other;
277 + return this.delegateMap.equals(that.delegateMap);
278 + }
279 + return false;
280 + }
281 +
282 + @Override
283 + public int hashCode() {
284 + return Objects.hash(delegateMap);
285 + }
286 +
287 +}
...@@ -18,6 +18,7 @@ package org.onosproject.store.primitives.impl; ...@@ -18,6 +18,7 @@ package org.onosproject.store.primitives.impl;
18 import java.util.function.Function; 18 import java.util.function.Function;
19 19
20 import org.onosproject.store.service.AsyncConsistentMap; 20 import org.onosproject.store.service.AsyncConsistentMap;
21 +import org.onosproject.store.service.AsyncConsistentTreeMap;
21 import org.onosproject.store.service.AsyncDistributedSet; 22 import org.onosproject.store.service.AsyncDistributedSet;
22 23
23 /** 24 /**
...@@ -100,4 +101,24 @@ public final class DistributedPrimitives { ...@@ -100,4 +101,24 @@ public final class DistributedPrimitives {
100 valueEncoder, 101 valueEncoder,
101 valueDecoder); 102 valueDecoder);
102 } 103 }
104 +
105 + /**
106 + * Creates an instance of {@code DistributedTreeMap} that transforms operations inputs and applies them
107 + * to corresponding operation in a different typed map and returns the output after reverse transforming it.
108 + *
109 + * @param map backing map
110 + * @param valueEncoder transformer for value type of returned map to value type of input map
111 + * @param valueDecoder transformer for value type of input map to value type of returned map
112 + * @param <V1> returned map value type
113 + * @param <V2> input map key type
114 + * @return new map
115 + */
116 + public static <V1, V2> AsyncConsistentTreeMap<V1> newTranscodingTreeMap(
117 + AsyncConsistentTreeMap<V2> map,
118 + Function<V1, V2> valueEncoder,
119 + Function<V2, V1> valueDecoder) {
120 + return new TranscodingAsyncConsistentTreeMap<>(map,
121 + valueEncoder,
122 + valueDecoder);
123 + }
103 } 124 }
......
...@@ -27,6 +27,7 @@ import org.onosproject.store.primitives.DistributedPrimitiveCreator; ...@@ -27,6 +27,7 @@ import org.onosproject.store.primitives.DistributedPrimitiveCreator;
27 import org.onosproject.store.service.AsyncAtomicCounter; 27 import org.onosproject.store.service.AsyncAtomicCounter;
28 import org.onosproject.store.service.AsyncAtomicValue; 28 import org.onosproject.store.service.AsyncAtomicValue;
29 import org.onosproject.store.service.AsyncConsistentMap; 29 import org.onosproject.store.service.AsyncConsistentMap;
30 +import org.onosproject.store.service.AsyncConsistentTreeMap;
30 import org.onosproject.store.service.AsyncDistributedSet; 31 import org.onosproject.store.service.AsyncDistributedSet;
31 import org.onosproject.store.service.AsyncLeaderElector; 32 import org.onosproject.store.service.AsyncLeaderElector;
32 import org.onosproject.store.service.Serializer; 33 import org.onosproject.store.service.Serializer;
...@@ -68,6 +69,12 @@ public class FederatedDistributedPrimitiveCreator implements DistributedPrimitiv ...@@ -68,6 +69,12 @@ public class FederatedDistributedPrimitiveCreator implements DistributedPrimitiv
68 } 69 }
69 70
70 @Override 71 @Override
72 + public <V> AsyncConsistentTreeMap<V> newAsyncConsistentTreeMap(String name,
73 + Serializer serializer) {
74 + return getCreator(name).newAsyncConsistentTreeMap(name, serializer);
75 + }
76 +
77 + @Override
71 public <E> AsyncDistributedSet<E> newAsyncDistributedSet(String name, Serializer serializer) { 78 public <E> AsyncDistributedSet<E> newAsyncDistributedSet(String name, Serializer serializer) {
72 return DistributedPrimitives.newSetFromMap(newAsyncConsistentMap(name, serializer)); 79 return DistributedPrimitives.newSetFromMap(newAsyncConsistentMap(name, serializer));
73 } 80 }
......
...@@ -47,6 +47,7 @@ import org.onosproject.store.service.AtomicCounterBuilder; ...@@ -47,6 +47,7 @@ import org.onosproject.store.service.AtomicCounterBuilder;
47 import org.onosproject.store.service.AtomicValueBuilder; 47 import org.onosproject.store.service.AtomicValueBuilder;
48 import org.onosproject.store.service.ConsistentMap; 48 import org.onosproject.store.service.ConsistentMap;
49 import org.onosproject.store.service.ConsistentMapBuilder; 49 import org.onosproject.store.service.ConsistentMapBuilder;
50 +import org.onosproject.store.service.ConsistentTreeMapBuilder;
50 import org.onosproject.store.service.DistributedSetBuilder; 51 import org.onosproject.store.service.DistributedSetBuilder;
51 import org.onosproject.store.service.EventuallyConsistentMapBuilder; 52 import org.onosproject.store.service.EventuallyConsistentMapBuilder;
52 import org.onosproject.store.service.LeaderElectorBuilder; 53 import org.onosproject.store.service.LeaderElectorBuilder;
...@@ -131,6 +132,12 @@ public class StorageManager implements StorageService, StorageAdminService { ...@@ -131,6 +132,12 @@ public class StorageManager implements StorageService, StorageAdminService {
131 } 132 }
132 133
133 @Override 134 @Override
135 + public <V> ConsistentTreeMapBuilder<V> consistentTreeMapBuilder() {
136 + return new DefaultConsistentTreeMapBuilder<V>(
137 + federatedPrimitiveCreator);
138 + }
139 +
140 + @Override
134 public <E> DistributedSetBuilder<E> setBuilder() { 141 public <E> DistributedSetBuilder<E> setBuilder() {
135 checkPermission(STORAGE_WRITE); 142 checkPermission(STORAGE_WRITE);
136 return new DefaultDistributedSetBuilder<>(() -> this.<E, Boolean>consistentMapBuilder()); 143 return new DefaultDistributedSetBuilder<>(() -> this.<E, Boolean>consistentMapBuilder());
......
...@@ -39,6 +39,7 @@ import java.util.function.Function; ...@@ -39,6 +39,7 @@ import java.util.function.Function;
39 import org.onlab.util.HexString; 39 import org.onlab.util.HexString;
40 import org.onosproject.store.primitives.DistributedPrimitiveCreator; 40 import org.onosproject.store.primitives.DistributedPrimitiveCreator;
41 import org.onosproject.store.primitives.resources.impl.AtomixConsistentMap; 41 import org.onosproject.store.primitives.resources.impl.AtomixConsistentMap;
42 +import org.onosproject.store.primitives.resources.impl.AtomixConsistentTreeMap;
42 import org.onosproject.store.primitives.resources.impl.AtomixCounter; 43 import org.onosproject.store.primitives.resources.impl.AtomixCounter;
43 import org.onosproject.store.primitives.resources.impl.AtomixLeaderElector; 44 import org.onosproject.store.primitives.resources.impl.AtomixLeaderElector;
44 import org.onosproject.store.primitives.resources.impl.AtomixWorkQueue; 45 import org.onosproject.store.primitives.resources.impl.AtomixWorkQueue;
...@@ -46,6 +47,7 @@ import org.onosproject.store.serializers.KryoNamespaces; ...@@ -46,6 +47,7 @@ import org.onosproject.store.serializers.KryoNamespaces;
46 import org.onosproject.store.service.AsyncAtomicCounter; 47 import org.onosproject.store.service.AsyncAtomicCounter;
47 import org.onosproject.store.service.AsyncAtomicValue; 48 import org.onosproject.store.service.AsyncAtomicValue;
48 import org.onosproject.store.service.AsyncConsistentMap; 49 import org.onosproject.store.service.AsyncConsistentMap;
50 +import org.onosproject.store.service.AsyncConsistentTreeMap;
49 import org.onosproject.store.service.AsyncDistributedSet; 51 import org.onosproject.store.service.AsyncDistributedSet;
50 import org.onosproject.store.service.AsyncLeaderElector; 52 import org.onosproject.store.service.AsyncLeaderElector;
51 import org.onosproject.store.service.DistributedPrimitive.Status; 53 import org.onosproject.store.service.DistributedPrimitive.Status;
...@@ -143,6 +145,30 @@ public class StoragePartitionClient implements DistributedPrimitiveCreator, Mana ...@@ -143,6 +145,30 @@ public class StoragePartitionClient implements DistributedPrimitiveCreator, Mana
143 } 145 }
144 146
145 @Override 147 @Override
148 + public <V> AsyncConsistentTreeMap<V> newAsyncConsistentTreeMap(String name, Serializer serializer) {
149 + AtomixConsistentTreeMap atomixConsistentTreeMap =
150 + client.getResource(name, AtomixConsistentTreeMap.class).join();
151 + Consumer<State> statusListener = state -> {
152 + atomixConsistentTreeMap.statusChangeListeners()
153 + .forEach(listener -> listener.accept(mapper.apply(state)));
154 + };
155 + resourceClient.client().onStateChange(statusListener);
156 + AsyncConsistentTreeMap<byte[]> rawMap =
157 + new DelegatingAsyncConsistentTreeMap<byte[]>(atomixConsistentTreeMap) {
158 + @Override
159 + public String name() {
160 + return name();
161 + }
162 + };
163 + AsyncConsistentTreeMap<V> transcodedMap =
164 + DistributedPrimitives.<V, byte[]>newTranscodingTreeMap(
165 + rawMap,
166 + value -> value == null ? null : serializer.encode(value),
167 + bytes -> serializer.decode(bytes));
168 + return transcodedMap;
169 + }
170 +
171 + @Override
146 public <E> AsyncDistributedSet<E> newAsyncDistributedSet(String name, Serializer serializer) { 172 public <E> AsyncDistributedSet<E> newAsyncDistributedSet(String name, Serializer serializer) {
147 return DistributedPrimitives.newSetFromMap(this.<E, Boolean>newAsyncConsistentMap(name, serializer)); 173 return DistributedPrimitives.newSetFromMap(this.<E, Boolean>newAsyncConsistentMap(name, serializer));
148 } 174 }
......
1 +/*
2 + * Copyright 2016 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 +package org.onosproject.store.primitives.impl;
18 +
19 +import com.google.common.collect.Maps;
20 +import org.onlab.util.Tools;
21 +import org.onosproject.store.primitives.TransactionId;
22 +import org.onosproject.store.service.AsyncConsistentTreeMap;
23 +import org.onosproject.store.service.MapEvent;
24 +import org.onosproject.store.service.MapEventListener;
25 +import org.onosproject.store.service.MapTransaction;
26 +import org.onosproject.store.service.Versioned;
27 +
28 +import java.util.Collection;
29 +import java.util.Map;
30 +import java.util.NavigableMap;
31 +import java.util.NavigableSet;
32 +import java.util.Set;
33 +import java.util.concurrent.CompletableFuture;
34 +import java.util.concurrent.Executor;
35 +import java.util.function.BiFunction;
36 +import java.util.function.Function;
37 +import java.util.function.Predicate;
38 +import java.util.stream.Collectors;
39 +
40 +/**
41 + * Created by admin on 8/3/16.
42 + */
43 +public class TranscodingAsyncConsistentTreeMap<V1, V2>
44 + implements AsyncConsistentTreeMap<V1> {
45 + private final AsyncConsistentTreeMap<V2> backingMap;
46 + private final Function<V2, V1> valueDecoder;
47 + private final Function<V1, V2> valueEncoder;
48 + private final Function<Versioned<V2>, Versioned<V1>>
49 + versionedValueTransform;
50 + private final Map<MapEventListener<String, V1>,
51 + TranscodingAsyncConsistentTreeMap.InternalBackingMapEventListener>
52 + listeners = Maps.newIdentityHashMap();
53 +
54 + public TranscodingAsyncConsistentTreeMap(
55 + AsyncConsistentTreeMap<V2> backingMap,
56 + Function<V1, V2> valueEncoder,
57 + Function<V2, V1> valueDecoder) {
58 + this.backingMap = backingMap;
59 + this.valueEncoder = v -> v == null ? null : valueEncoder.apply(v);
60 + this.valueDecoder = v -> v == null ? null : valueDecoder.apply(v);
61 + this.versionedValueTransform = v -> v == null ? null :
62 + v.map(valueDecoder);
63 + }
64 + @Override
65 + public CompletableFuture<String> firstKey() {
66 + return backingMap.firstKey();
67 + }
68 +
69 + @Override
70 + public CompletableFuture<String> lastKey() {
71 + return backingMap.lastKey();
72 + }
73 +
74 + @Override
75 + public CompletableFuture<Map.Entry<String, Versioned<V1>>>
76 + ceilingEntry(String key) {
77 + return backingMap.ceilingEntry(key)
78 + .thenApply(
79 + entry ->
80 + Maps.immutableEntry(
81 + entry.getKey(),
82 + entry.getValue().map(valueDecoder)));
83 + }
84 +
85 + @Override
86 + public CompletableFuture<Map.Entry<String, Versioned<V1>>>
87 + floorEntry(String key) {
88 + return backingMap.floorEntry(key)
89 + .thenApply(
90 + entry ->
91 + Maps.immutableEntry(
92 + entry.getKey(),
93 + entry.getValue().map(valueDecoder)));
94 + }
95 +
96 + @Override
97 + public CompletableFuture<Map.Entry<String, Versioned<V1>>>
98 + higherEntry(String key) {
99 + return backingMap
100 + .higherEntry(key)
101 + .thenApply(entry ->
102 + Maps.immutableEntry(
103 + entry.getKey(),
104 + entry.getValue().map(valueDecoder)));
105 +}
106 +
107 + @Override
108 + public CompletableFuture<Map.Entry<String, Versioned<V1>>>
109 + lowerEntry(String key) {
110 + return backingMap.lowerEntry(key).thenApply(
111 + entry ->
112 + Maps.immutableEntry(
113 + entry.getKey(),
114 + entry.getValue().map(valueDecoder)));
115 + }
116 +
117 + @Override
118 + public CompletableFuture<Map.Entry<String, Versioned<V1>>>
119 + firstEntry() {
120 + return backingMap.firstEntry()
121 + .thenApply(entry ->
122 + Maps.immutableEntry(
123 + entry.getKey(),
124 + entry.getValue().map(valueDecoder)));
125 + }
126 +
127 + @Override
128 + public CompletableFuture<Map.Entry<String, Versioned<V1>>>
129 + lastEntry() {
130 + return backingMap.lastEntry()
131 + .thenApply(
132 + entry -> Maps.immutableEntry(
133 + entry.getKey(),
134 + entry.getValue().map(valueDecoder)));
135 + }
136 +
137 + @Override
138 + public CompletableFuture<Map.Entry<String, Versioned<V1>>>
139 + pollFirstEntry() {
140 + return backingMap.pollFirstEntry()
141 + .thenApply(
142 + entry -> Maps.immutableEntry(
143 + entry.getKey(),
144 + entry.getValue().map(valueDecoder)));
145 + }
146 +
147 + @Override
148 + public CompletableFuture<Map.Entry<String, Versioned<V1>>>
149 + pollLastEntry() {
150 + return backingMap.pollLastEntry()
151 + .thenApply(entry -> Maps.immutableEntry(
152 + entry.getKey(),
153 + entry.getValue().map(valueDecoder)));
154 + }
155 +
156 + @Override
157 + public CompletableFuture<String> lowerKey(String key) {
158 + return backingMap.lowerKey(key);
159 + }
160 +
161 + @Override
162 + public CompletableFuture<String> floorKey(String key) {
163 + return backingMap.floorKey(key);
164 + }
165 +
166 + @Override
167 + public CompletableFuture<String> ceilingKey(String key) {
168 + return backingMap.ceilingKey(key);
169 + }
170 +
171 + @Override
172 + public CompletableFuture<String> higherKey(String key) {
173 + return backingMap.higherKey(key);
174 + }
175 +
176 + @Override
177 + public CompletableFuture<NavigableSet<String>> navigableKeySet() {
178 + return backingMap.navigableKeySet();
179 + }
180 +
181 + @Override
182 + public CompletableFuture<NavigableMap<String, V1>> subMap(
183 + String upperKey,
184 + String lowerKey,
185 + boolean inclusiveUpper,
186 + boolean inclusiveLower) {
187 + throw new UnsupportedOperationException("This operation is not yet" +
188 + "supported.");
189 + }
190 +
191 + @Override
192 + public String name() {
193 + return backingMap.name();
194 + }
195 +
196 + @Override
197 + public CompletableFuture<Integer> size() {
198 + return backingMap.size();
199 + }
200 +
201 + @Override
202 + public CompletableFuture<Boolean> containsKey(String key) {
203 + return backingMap.containsKey(key);
204 + }
205 +
206 + @Override
207 + public CompletableFuture<Boolean> containsValue(V1 value) {
208 + return backingMap.containsValue(valueEncoder.apply(value));
209 + }
210 +
211 + @Override
212 + public CompletableFuture<Versioned<V1>> get(String key) {
213 + return backingMap.get(key).thenApply(value -> value.map(valueDecoder));
214 + }
215 +
216 + @Override
217 + public CompletableFuture<Versioned<V1>> computeIf(
218 + String key, Predicate<? super V1> condition,
219 + BiFunction<? super String, ? super V1, ? extends V1>
220 + remappingFunction) {
221 + try {
222 + return backingMap
223 + .computeIf(
224 + key,
225 + v -> condition.test(valueDecoder.apply(v)),
226 + (k, v) -> valueEncoder
227 + .apply(
228 + remappingFunction.apply(
229 + key,
230 + valueDecoder.apply(v))))
231 + .thenApply(versionedValueTransform);
232 + } catch (Exception e) {
233 + return Tools.exceptionalFuture(e);
234 + }
235 + }
236 +
237 + @Override
238 + public CompletableFuture<Versioned<V1>> put(String key, V1 value) {
239 + return backingMap.put(key, valueEncoder.apply(value))
240 + .thenApply(v -> v.map(valueDecoder));
241 + }
242 +
243 + @Override
244 + public CompletableFuture<Versioned<V1>> putAndGet(String key, V1 value) {
245 + return backingMap.putAndGet(key, valueEncoder.apply(value))
246 + .thenApply(v -> v.map(valueDecoder));
247 + }
248 +
249 + @Override
250 + public CompletableFuture<Versioned<V1>> remove(String key) {
251 + return backingMap.remove(key).thenApply(v -> v.map(valueDecoder));
252 + }
253 +
254 + @Override
255 + public CompletableFuture<Void> clear() {
256 + return backingMap.clear();
257 + }
258 +
259 + @Override
260 + public CompletableFuture<Set<String>> keySet() {
261 + return backingMap.keySet();
262 + }
263 +
264 + @Override
265 + public CompletableFuture<Collection<Versioned<V1>>> values() {
266 + return backingMap.values().thenApply(valueSet -> valueSet.stream()
267 + .map(v -> v.map(valueDecoder)).collect(Collectors.toSet()));
268 + }
269 +
270 + @Override
271 + public CompletableFuture<Set<Map.Entry<String, Versioned<V1>>>>
272 + entrySet() {
273 + return backingMap.entrySet()
274 + .thenApply(
275 + entries -> entries
276 + .stream()
277 + .map(entry ->
278 + Maps.immutableEntry(entry.getKey(),
279 + entry.getValue()
280 + .map(valueDecoder)))
281 + .collect(Collectors.toSet()));
282 + }
283 +
284 + @Override
285 + public CompletableFuture<Versioned<V1>> putIfAbsent(String key, V1 value) {
286 + return backingMap.putIfAbsent(key, valueEncoder.apply(value))
287 + .thenApply(v -> v.map(valueDecoder));
288 + }
289 +
290 + @Override
291 + public CompletableFuture<Boolean> remove(String key, V1 value) {
292 + return backingMap.remove(key, valueEncoder.apply(value));
293 + }
294 +
295 + @Override
296 + public CompletableFuture<Boolean> remove(String key, long version) {
297 + return backingMap.remove(key, version);
298 + }
299 +
300 + @Override
301 + public CompletableFuture<Versioned<V1>> replace(String key, V1 value) {
302 + return backingMap.replace(key, valueEncoder.apply(value))
303 + .thenApply(v -> v.map(valueDecoder));
304 + }
305 +
306 + @Override
307 + public CompletableFuture<Boolean> replace(String key, V1 oldValue,
308 + V1 newValue) {
309 + return backingMap.replace(key, valueEncoder.apply(oldValue),
310 + valueEncoder.apply(newValue));
311 + }
312 +
313 + @Override
314 + public CompletableFuture<Boolean> replace(String key, long oldVersion,
315 + V1 newValue) {
316 + return backingMap.replace(key, oldVersion,
317 + valueEncoder.apply(newValue));
318 + }
319 +
320 + @Override
321 + public CompletableFuture<Void> addListener(
322 + MapEventListener<String, V1> listener,
323 + Executor executor) {
324 + InternalBackingMapEventListener backingMapEventListener =
325 + listeners.computeIfAbsent(
326 + listener,
327 + k -> new InternalBackingMapEventListener(listener));
328 + return backingMap.addListener(backingMapEventListener, executor);
329 + }
330 +
331 + @Override
332 + public CompletableFuture<Void> removeListener(
333 + MapEventListener<String, V1> listener) {
334 + InternalBackingMapEventListener backingMapEventListener =
335 + listeners.remove(listener);
336 + if (backingMapEventListener == null) {
337 + return CompletableFuture.completedFuture(null);
338 + } else {
339 + return backingMap.removeListener(backingMapEventListener);
340 + }
341 + }
342 +
343 + @Override
344 + public CompletableFuture<Boolean> prepare(
345 + MapTransaction<String, V1> transaction) {
346 + throw new UnsupportedOperationException("This operation is not yet " +
347 + "supported.");
348 + }
349 +
350 + @Override
351 + public CompletableFuture<Void> commit(TransactionId transactionId) {
352 + throw new UnsupportedOperationException("This operation is not yet " +
353 + "supported."); }
354 +
355 + @Override
356 + public CompletableFuture<Void> rollback(TransactionId transactionId) {
357 + throw new UnsupportedOperationException("This operation is not yet " +
358 + "supported."); }
359 +
360 + @Override
361 + public CompletableFuture<Boolean> prepareAndCommit(
362 + MapTransaction<String, V1> transaction) {
363 + throw new UnsupportedOperationException("This operation is not yet " +
364 + "supported."); }
365 + private class InternalBackingMapEventListener
366 + implements MapEventListener<String, V2> {
367 +
368 + private final MapEventListener<String, V1> listener;
369 +
370 + InternalBackingMapEventListener(
371 + MapEventListener<String, V1> listener) {
372 + this.listener = listener;
373 + }
374 +
375 + @Override
376 + public void event(MapEvent<String, V2> event) {
377 + listener.event(new MapEvent<String, V1>(
378 + event.name(),
379 + event.key(),
380 + event.newValue() != null ?
381 + event.newValue().map(valueDecoder) : null,
382 + event.oldValue() != null ?
383 + event.oldValue().map(valueDecoder) : null));
384 + }
385 + }
386 +}