Eliminate EntityOwnershipChange
[mdsal.git] / singleton-service / mdsal-singleton-dom-impl / src / test / java / org / opendaylight / mdsal / singleton / dom / impl / DOMClusterSingletonServiceProviderAsyncImplTest.java
1 /*
2  * Copyright (c) 2016 Cisco Systems, Inc. and others.  All rights reserved.
3  *
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
7  */
8 package org.opendaylight.mdsal.singleton.dom.impl;
9
10 import static org.junit.Assert.assertEquals;
11 import static org.junit.Assert.assertNotNull;
12 import static org.mockito.Mockito.never;
13 import static org.mockito.Mockito.verify;
14 import static org.opendaylight.mdsal.eos.common.api.EntityOwnershipStateChange.LOCAL_OWNERSHIP_GRANTED;
15 import static org.opendaylight.mdsal.eos.common.api.EntityOwnershipStateChange.LOCAL_OWNERSHIP_LOST_NEW_OWNER;
16 import static org.opendaylight.mdsal.eos.common.api.EntityOwnershipStateChange.LOCAL_OWNERSHIP_RETAINED_WITH_NO_CHANGE;
17 import static org.opendaylight.mdsal.eos.common.api.EntityOwnershipStateChange.REMOTE_OWNERSHIP_CHANGED;
18
19 import com.google.common.util.concurrent.ListenableFuture;
20 import com.google.common.util.concurrent.SettableFuture;
21 import java.util.Timer;
22 import java.util.TimerTask;
23 import org.junit.AfterClass;
24 import org.junit.BeforeClass;
25 import org.junit.Test;
26 import org.junit.runner.RunWith;
27 import org.mockito.junit.MockitoJUnitRunner;
28 import org.opendaylight.mdsal.singleton.common.api.ClusterSingletonService;
29 import org.opendaylight.mdsal.singleton.common.api.ClusterSingletonServiceRegistration;
30
31 /*
32  * Testing {@link DOMClusterSingletonServiceProviderImpl} implementation
33  */
34 @RunWith(MockitoJUnitRunner.StrictStubs.class)
35 public final class DOMClusterSingletonServiceProviderAsyncImplTest extends AbstractDOMClusterServiceProviderTest {
36     /*
37      * Test implementation of {@link ClusterSingletonService}
38      */
39     public static class TestClusterSingletonAsyncServiceInstance extends TestClusterSingletonService {
40         @Override
41         public ListenableFuture<Void> closeServiceInstance() {
42             super.closeServiceInstance();
43
44             final SettableFuture<Void> future = SettableFuture.create();
45             TIMER.schedule(new TimerTask() {
46                 @Override
47                 public void run() {
48                     future.set(null);
49                 }
50             }, ASYNC_TIME_DELAY_MILLIS);
51             return future;
52         }
53     }
54
55     public static final long ASYNC_TIME_DELAY_MILLIS = 100L;
56     public static Timer TIMER;
57
58     @BeforeClass
59     public static void asyncInitTest() {
60         TIMER = new Timer();
61     }
62
63     @AfterClass
64     public static void cleanTest() {
65         TIMER.cancel();
66     }
67
68     @Override
69     TestClusterSingletonService instantiateService() {
70         return new TestClusterSingletonAsyncServiceInstance();
71     }
72
73     /**
74      * Test GoldPath for takeLeadership with ownership result MASTER {@link ClusterSingletonService}.
75      *
76      * @throws Exception if the condition does not meet
77      */
78     @Test
79     public void takeDoubleLeadershipClusterSingletonServiceTest() throws Exception {
80         final ClusterSingletonServiceRegistration reg = clusterSingletonServiceProvider
81                 .registerClusterSingletonService(clusterSingletonService);
82         assertNotNull(reg);
83         verify(mockEos).registerCandidate(ENTITY);
84         clusterSingletonServiceProvider.ownershipChanged(ENTITY, LOCAL_OWNERSHIP_GRANTED, false);
85         verify(mockEos).registerCandidate(DOUBLE_ENTITY);
86         assertEquals(TestClusterSingletonServiceState.INITIALIZED, clusterSingletonService.getServiceState());
87         clusterSingletonServiceProvider.ownershipChanged(DOUBLE_ENTITY, LOCAL_OWNERSHIP_GRANTED, false);
88         assertEquals(TestClusterSingletonServiceState.STARTED, clusterSingletonService.getServiceState());
89         clusterSingletonServiceProvider.ownershipChanged(ENTITY, LOCAL_OWNERSHIP_LOST_NEW_OWNER, false);
90         assertEquals(TestClusterSingletonServiceState.DESTROYED, clusterSingletonService.getServiceState());
91         Thread.sleep(ASYNC_TIME_DELAY_MILLIS * 2);
92         verify(mockDoubleEntityCandReg).close();
93         clusterSingletonServiceProvider.ownershipChanged(ENTITY, LOCAL_OWNERSHIP_GRANTED, false);
94         assertEquals(TestClusterSingletonServiceState.DESTROYED, clusterSingletonService.getServiceState());
95         clusterSingletonServiceProvider.ownershipChanged(DOUBLE_ENTITY, REMOTE_OWNERSHIP_CHANGED, false);
96         clusterSingletonServiceProvider.ownershipChanged(DOUBLE_ENTITY, LOCAL_OWNERSHIP_GRANTED, false);
97         assertEquals(TestClusterSingletonServiceState.STARTED, clusterSingletonService.getServiceState());
98         verify(mockEosDoubleEntityListReg, never()).close();
99         verify(mockEosEntityListReg, never()).close();
100         verify(mockEntityCandReg, never()).close();
101     }
102
103     /**
104      * Test checks unexpected change for MASTER-TO-SLAVE double Candidate role change.
105      *
106      * @throws Exception if the condition does not meet
107      */
108     @Test
109     public void unexpectedLostLeadershipDoubleCandidateTest() throws Exception {
110         final ClusterSingletonServiceRegistration reg = clusterSingletonServiceProvider
111                 .registerClusterSingletonService(clusterSingletonService);
112         assertNotNull(reg);
113         verify(mockEos).registerCandidate(ENTITY);
114         clusterSingletonServiceProvider.ownershipChanged(ENTITY, LOCAL_OWNERSHIP_GRANTED, false);
115         verify(mockEos).registerCandidate(DOUBLE_ENTITY);
116         assertEquals(TestClusterSingletonServiceState.INITIALIZED, clusterSingletonService.getServiceState());
117         clusterSingletonServiceProvider.ownershipChanged(DOUBLE_ENTITY, REMOTE_OWNERSHIP_CHANGED, false);
118         assertEquals(TestClusterSingletonServiceState.INITIALIZED, clusterSingletonService.getServiceState());
119         clusterSingletonServiceProvider.ownershipChanged(DOUBLE_ENTITY, LOCAL_OWNERSHIP_GRANTED, false);
120         assertEquals(TestClusterSingletonServiceState.STARTED, clusterSingletonService.getServiceState());
121         clusterSingletonServiceProvider.ownershipChanged(DOUBLE_ENTITY, LOCAL_OWNERSHIP_LOST_NEW_OWNER, false);
122         assertEquals(TestClusterSingletonServiceState.DESTROYED, clusterSingletonService.getServiceState());
123         Thread.sleep(ASYNC_TIME_DELAY_MILLIS * 2);
124         verify(mockEosDoubleEntityListReg, never()).close();
125         verify(mockEntityCandReg, never()).close();
126         verify(mockDoubleEntityCandReg, never()).close();
127         reg.close();
128         verify(mockEosDoubleEntityListReg, never()).close();
129         verify(mockEntityCandReg).close();
130         verify(mockDoubleEntityCandReg).close();
131     }
132
133     /**
134      * Test checks inJeopardy Cluster Node state for Master Instance.
135      *
136      * @throws Exception if the condition does not meet
137      */
138     @Test
139     public void inJeopardyMasterTest() throws Exception {
140         final ClusterSingletonServiceRegistration reg = clusterSingletonServiceProvider
141                 .registerClusterSingletonService(clusterSingletonService);
142         assertNotNull(reg);
143         verify(mockEos).registerCandidate(ENTITY);
144         clusterSingletonServiceProvider.ownershipChanged(ENTITY, LOCAL_OWNERSHIP_GRANTED, false);
145         verify(mockEos).registerCandidate(DOUBLE_ENTITY);
146         assertEquals(TestClusterSingletonServiceState.INITIALIZED, clusterSingletonService.getServiceState());
147         clusterSingletonServiceProvider.ownershipChanged(DOUBLE_ENTITY, REMOTE_OWNERSHIP_CHANGED, false);
148         assertEquals(TestClusterSingletonServiceState.INITIALIZED, clusterSingletonService.getServiceState());
149         clusterSingletonServiceProvider.ownershipChanged(DOUBLE_ENTITY, LOCAL_OWNERSHIP_GRANTED, false);
150         assertEquals(TestClusterSingletonServiceState.STARTED, clusterSingletonService.getServiceState());
151         clusterSingletonServiceProvider.ownershipChanged(ENTITY, LOCAL_OWNERSHIP_RETAINED_WITH_NO_CHANGE, true);
152         assertEquals(TestClusterSingletonServiceState.STARTED, clusterSingletonService.getServiceState());
153         clusterSingletonServiceProvider.ownershipChanged(DOUBLE_ENTITY, LOCAL_OWNERSHIP_RETAINED_WITH_NO_CHANGE, true);
154         assertEquals(TestClusterSingletonServiceState.DESTROYED, clusterSingletonService.getServiceState());
155         Thread.sleep(ASYNC_TIME_DELAY_MILLIS * 2);
156         verify(mockEosEntityListReg, never()).close();
157         verify(mockEosDoubleEntityListReg, never()).close();
158         verify(mockEntityCandReg, never()).close();
159         verify(mockDoubleEntityCandReg, never()).close();
160     }
161
162     /**
163      * Test checks close processing for {@link ClusterSingletonServiceRegistration}.
164      *
165      * @throws Exception if the condition does not meet
166      */
167     @Test
168     public void closeClusterSingletonServiceRegistrationMasterTest() throws Exception {
169         final ClusterSingletonServiceRegistration reg = clusterSingletonServiceProvider
170                 .registerClusterSingletonService(clusterSingletonService);
171         assertNotNull(reg);
172         assertEquals(TestClusterSingletonServiceState.INITIALIZED, clusterSingletonService.getServiceState());
173         verify(mockEos).registerCandidate(ENTITY);
174         clusterSingletonServiceProvider.ownershipChanged(ENTITY, LOCAL_OWNERSHIP_GRANTED, false);
175         verify(mockEos).registerCandidate(DOUBLE_ENTITY);
176         clusterSingletonServiceProvider.ownershipChanged(DOUBLE_ENTITY, LOCAL_OWNERSHIP_GRANTED, false);
177         assertEquals(TestClusterSingletonServiceState.STARTED, clusterSingletonService.getServiceState());
178         reg.close();
179         verify(mockEntityCandReg).close();
180         verify(mockDoubleEntityCandReg, never()).close();
181         assertEquals(TestClusterSingletonServiceState.DESTROYED, clusterSingletonService.getServiceState());
182         Thread.sleep(ASYNC_TIME_DELAY_MILLIS * 2);
183         verify(mockDoubleEntityCandReg).close();
184         verify(mockEosEntityListReg, never()).close();
185         verify(mockEosDoubleEntityListReg, never()).close();
186     }
187
188     /**
189      * Test checks close processing for {@link ClusterSingletonServiceRegistration}.
190      *
191      * @throws Exception if the condition does not meet
192      */
193     @Test
194     public void closeClusterSingletonServiceRegistrationMasterCloseWithNotificationTimesTest() throws Exception {
195         final ClusterSingletonServiceRegistration reg = clusterSingletonServiceProvider
196                 .registerClusterSingletonService(clusterSingletonService);
197         assertNotNull(reg);
198         assertEquals(TestClusterSingletonServiceState.INITIALIZED, clusterSingletonService.getServiceState());
199         verify(mockEos).registerCandidate(ENTITY);
200         clusterSingletonServiceProvider.ownershipChanged(ENTITY, LOCAL_OWNERSHIP_GRANTED, false);
201         verify(mockEos).registerCandidate(DOUBLE_ENTITY);
202         clusterSingletonServiceProvider.ownershipChanged(DOUBLE_ENTITY, LOCAL_OWNERSHIP_GRANTED, false);
203         assertEquals(TestClusterSingletonServiceState.STARTED, clusterSingletonService.getServiceState());
204         reg.close();
205         verify(mockEntityCandReg).close();
206         verify(mockDoubleEntityCandReg, never()).close();
207         assertEquals(TestClusterSingletonServiceState.DESTROYED, clusterSingletonService.getServiceState());
208         Thread.sleep(ASYNC_TIME_DELAY_MILLIS * 2);
209         verify(mockDoubleEntityCandReg).close();
210         verify(mockEosEntityListReg, never()).close();
211         verify(mockEosDoubleEntityListReg, never()).close();
212     }
213
214     /**
215      * Test checks close processing for {@link ClusterSingletonServiceRegistration}.
216      *
217      * @throws Exception if the condition does not meet
218      */
219     @Test
220     public void closeClusterSingletonServiceRegistrationMasterCloseCoupleTimesTest() throws Exception {
221         final ClusterSingletonServiceRegistration reg = clusterSingletonServiceProvider
222                 .registerClusterSingletonService(clusterSingletonService);
223         assertNotNull(reg);
224         assertEquals(TestClusterSingletonServiceState.INITIALIZED, clusterSingletonService.getServiceState());
225         verify(mockEos).registerCandidate(ENTITY);
226         clusterSingletonServiceProvider.ownershipChanged(ENTITY, LOCAL_OWNERSHIP_GRANTED, false);
227         verify(mockEos).registerCandidate(DOUBLE_ENTITY);
228         clusterSingletonServiceProvider.ownershipChanged(DOUBLE_ENTITY, LOCAL_OWNERSHIP_GRANTED, false);
229         assertEquals(TestClusterSingletonServiceState.STARTED, clusterSingletonService.getServiceState());
230         reg.close();
231         reg.close();
232         verify(mockEntityCandReg).close();
233         verify(mockDoubleEntityCandReg, never()).close();
234         assertEquals(TestClusterSingletonServiceState.DESTROYED, clusterSingletonService.getServiceState());
235
236         Thread.sleep(ASYNC_TIME_DELAY_MILLIS * 2);
237         verify(mockEosEntityListReg, never()).close();
238         verify(mockEosDoubleEntityListReg, never()).close();
239         verify(mockDoubleEntityCandReg).close();
240     }
241 }