2 * Copyright (c) 2015 Cisco Systems, Inc. and others. All rights reserved.
4 * This program and the accompanying materials are made available under the
5 * terms of the Eclipse Public License v1.0 which accompanies this distribution,
6 * and is available at http://www.eclipse.org/legal/epl-v10.html
9 package org.opendaylight.controller.cluster.datastore.entityownership;
11 import static org.opendaylight.controller.cluster.datastore.entityownership.EntityOwnersModel.entityTypeFromEntityPath;
13 import com.google.common.base.Optional;
14 import com.google.common.base.Strings;
15 import com.romix.scala.collection.concurrent.TrieMap;
16 import java.util.Collection;
17 import java.util.HashMap;
19 import javax.annotation.Nonnull;
20 import org.opendaylight.yangtools.yang.data.api.schema.LeafNode;
21 import org.opendaylight.yangtools.yang.data.api.schema.NormalizedNode;
22 import org.opendaylight.yangtools.yang.data.api.schema.tree.DataTreeCandidate;
23 import org.opendaylight.yangtools.yang.data.api.schema.tree.DataTreeCandidateNode;
26 * EntityOwnershipStatistics is a utility class that keeps track of ownership statistics for the candidates and
27 * caches it for quick count queries.
29 * While the entity ownership model does maintain the information about which entity is owned by which candidate
30 * finding out how many entities of a given type are owned by a given candidate is not an efficient query.
32 class EntityOwnershipStatistics extends AbstractEntityOwnerChangeListener {
34 private final TrieMap<String, TrieMap<String, Long>> statistics = new TrieMap<>();
36 EntityOwnershipStatistics(){
40 public void onDataTreeChanged(@Nonnull Collection<DataTreeCandidate> changes) {
41 for (DataTreeCandidate change : changes) {
42 DataTreeCandidateNode changeRoot = change.getRootNode();
43 LeafNode<?> ownerLeaf = (LeafNode<?>) changeRoot.getDataAfter().get();
44 String entityType = entityTypeFromEntityPath(change.getRootPath());
45 String newOwner = extractOwner(ownerLeaf);
46 if (!Strings.isNullOrEmpty(newOwner)) {
47 updateStatistics(entityType, newOwner, 1);
50 Optional<NormalizedNode<?, ?>> dataBefore = changeRoot.getDataBefore();
51 if (dataBefore.isPresent()) {
52 String origOwner = extractOwner((LeafNode<?>) changeRoot.getDataBefore().get());
53 if (!Strings.isNullOrEmpty(origOwner)) {
54 updateStatistics(entityType, origOwner, -1);
60 Map<String, Map<String, Long>> all() {
61 Map<String, Map<String, Long>> snapshot = new HashMap<>();
62 for (String entityType : statistics.readOnlySnapshot().keySet()) {
63 snapshot.put(entityType, byEntityType(entityType));
68 Map<String, Long> byEntityType(String entityType) {
69 if (statistics.get(entityType) != null) {
70 return statistics.get(entityType).readOnlySnapshot();
72 return new HashMap<>();
75 private void updateStatistics(String entityType, String candidateName, long count) {
76 Map<String, Long> map = statistics.get(entityType);
78 map = new TrieMap<>();
79 map.put(candidateName, count);
80 statistics.put(entityType, map);
82 Long candidateOwnedEntities = map.get(candidateName);
83 if (candidateOwnedEntities == null) {
84 map.put(candidateName, count);
86 map.put(candidateName, candidateOwnedEntities + count);