Yuta HIGUCHI

initial sketch of ReplicaInfoService.

Change-Id: I364b023aa6be69cabb184b92fd7a0dadd5215ec9
1 +package org.onlab.onos.store.flow;
2 +
3 +import static com.google.common.base.Preconditions.checkNotNull;
4 +
5 +import java.util.Collection;
6 +import java.util.Collections;
7 +
8 +import org.onlab.onos.cluster.NodeId;
9 +
10 +import com.google.common.base.Optional;
11 +
12 +/**
13 + * Class to represent placement information about Master/Backup copy.
14 + */
15 +public final class ReplicaInfo {
16 +
17 + private final Optional<NodeId> master;
18 + private final Collection<NodeId> backups;
19 +
20 + /**
21 + * Creates a ReplicaInfo instance.
22 + *
23 + * @param master NodeId of the node where the master copy should be
24 + * @param backups collection of NodeId, where backup copies should be placed
25 + */
26 + public ReplicaInfo(NodeId master, Collection<NodeId> backups) {
27 + this.master = Optional.fromNullable(master);
28 + this.backups = checkNotNull(backups);
29 + }
30 +
31 + /**
32 + * Returns the NodeId, if there is a Node where the master copy should be.
33 + *
34 + * @return NodeId, where the master copy should be placed
35 + */
36 + public Optional<NodeId> master() {
37 + return master;
38 + }
39 +
40 + /**
41 + * Returns the collection of NodeId, where backup copies should be placed.
42 + *
43 + * @return collection of NodeId, where backup copies should be placed
44 + */
45 + public Collection<NodeId> backups() {
46 + return backups;
47 + }
48 +
49 + // for Serializer
50 + private ReplicaInfo() {
51 + this.master = Optional.absent();
52 + this.backups = Collections.emptyList();
53 + }
54 +}
1 +package org.onlab.onos.store.flow;
2 +
3 +import static com.google.common.base.Preconditions.checkNotNull;
4 +
5 +import org.onlab.onos.event.AbstractEvent;
6 +import org.onlab.onos.net.DeviceId;
7 +
8 +/**
9 + * Describes a device replicainfo event.
10 + */
11 +public class ReplicaInfoEvent extends AbstractEvent<ReplicaInfoEvent.Type, DeviceId> {
12 +
13 + private final ReplicaInfo replicaInfo;
14 +
15 + /**
16 + * Types of Replica info event.
17 + */
18 + public enum Type {
19 + /**
20 + * Event to notify that master placement should be changed.
21 + */
22 + MASTER_CHANGED,
23 + //
24 + // BACKUPS_CHANGED?
25 + }
26 +
27 +
28 + /**
29 + * Creates an event of a given type and for the specified device,
30 + * and replica info.
31 + *
32 + * @param type replicainfo event type
33 + * @param device event device subject
34 + * @param replicaInfo replicainfo
35 + */
36 + public ReplicaInfoEvent(Type type, DeviceId device, ReplicaInfo replicaInfo) {
37 + super(type, device);
38 + this.replicaInfo = checkNotNull(replicaInfo);
39 + }
40 +
41 + /**
42 + * Returns the current replica information for the subject.
43 + *
44 + * @return replica information for the subject
45 + */
46 + public ReplicaInfo replicaInfo() {
47 + return replicaInfo;
48 + };
49 +}
1 +package org.onlab.onos.store.flow;
2 +
3 +import org.onlab.onos.event.EventListener;
4 +
5 +/**
6 + * Entity capable of receiving Replica placement information-related events.
7 + */
8 +public interface ReplicaInfoEventListener extends EventListener<ReplicaInfoEvent> {
9 +
10 +}
11 +
1 +package org.onlab.onos.store.flow;
2 +
3 +import org.onlab.onos.net.DeviceId;
4 +
5 +/**
6 + * Service to return where the Replica should be placed.
7 + */
8 +public interface ReplicaInfoService {
9 +
10 + // returns where it should be.
11 + /**
12 + * Returns the placement information for given Device.
13 + *
14 + * @param deviceId identifier of the device
15 + * @return placement information
16 + */
17 + ReplicaInfo getReplicaInfoFor(DeviceId deviceId);
18 +}
1 +package org.onlab.onos.store.flow.impl;
2 +
3 +import static org.slf4j.LoggerFactory.getLogger;
4 +import static org.onlab.onos.store.flow.ReplicaInfoEvent.Type.MASTER_CHANGED;
5 +
6 +import java.util.Collections;
7 +import java.util.List;
8 +
9 +import org.apache.felix.scr.annotations.Activate;
10 +import org.apache.felix.scr.annotations.Component;
11 +import org.apache.felix.scr.annotations.Deactivate;
12 +import org.apache.felix.scr.annotations.Reference;
13 +import org.apache.felix.scr.annotations.ReferenceCardinality;
14 +import org.apache.felix.scr.annotations.Service;
15 +import org.onlab.onos.cluster.NodeId;
16 +import org.onlab.onos.event.AbstractListenerRegistry;
17 +import org.onlab.onos.event.EventDeliveryService;
18 +import org.onlab.onos.mastership.MastershipEvent;
19 +import org.onlab.onos.mastership.MastershipListener;
20 +import org.onlab.onos.mastership.MastershipService;
21 +import org.onlab.onos.net.DeviceId;
22 +import org.onlab.onos.store.flow.ReplicaInfo;
23 +import org.onlab.onos.store.flow.ReplicaInfoEvent;
24 +import org.onlab.onos.store.flow.ReplicaInfoEventListener;
25 +import org.onlab.onos.store.flow.ReplicaInfoService;
26 +import org.slf4j.Logger;
27 +
28 +/**
29 + * Manages replica placement information.
30 + */
31 +@Component(immediate = true)
32 +@Service
33 +public class ReplicaInfoManager implements ReplicaInfoService {
34 +
35 + private final Logger log = getLogger(getClass());
36 +
37 + private final MastershipListener mastershipListener = new InternalMastershipListener();
38 +
39 + @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
40 + protected EventDeliveryService eventDispatcher;
41 +
42 + @Reference(cardinality = ReferenceCardinality.MANDATORY_UNARY)
43 + protected MastershipService mastershipService;
44 +
45 + protected final AbstractListenerRegistry<ReplicaInfoEvent, ReplicaInfoEventListener>
46 + listenerRegistry = new AbstractListenerRegistry<>();
47 +
48 + @Activate
49 + public void activate() {
50 + eventDispatcher.addSink(ReplicaInfoEvent.class, listenerRegistry);
51 + mastershipService.addListener(mastershipListener);
52 + log.info("Started");
53 + }
54 +
55 + @Deactivate
56 + public void deactivate() {
57 + eventDispatcher.removeSink(ReplicaInfoEvent.class);
58 + mastershipService.removeListener(mastershipListener);
59 + log.info("Stopped");
60 + }
61 +
62 + @Override
63 + public ReplicaInfo getReplicaInfoFor(DeviceId deviceId) {
64 + // TODO: populate backup List when we reach the point we need them.
65 + return new ReplicaInfo(mastershipService.getMasterFor(deviceId),
66 + Collections.<NodeId>emptyList());
67 + }
68 +
69 + final class InternalMastershipListener implements MastershipListener {
70 +
71 + @Override
72 + public void event(MastershipEvent event) {
73 + // TODO: distinguish stby list update, when MastershipService,
74 + // start publishing them
75 + final List<NodeId> standbyList = Collections.<NodeId>emptyList();
76 + eventDispatcher.post(new ReplicaInfoEvent(MASTER_CHANGED,
77 + event.subject(),
78 + new ReplicaInfo(event.master(), standbyList)));
79 + }
80 + }
81 +
82 +}
...@@ -2,4 +2,4 @@ ...@@ -2,4 +2,4 @@
2 * Implementation of the distributed flow rule store using p2p synchronization 2 * Implementation of the distributed flow rule store using p2p synchronization
3 * protocol. 3 * protocol.
4 */ 4 */
5 -package org.onlab.onos.store.flow.impl;
...\ No newline at end of file ...\ No newline at end of file
5 +package org.onlab.onos.store.flow.impl;
......