2 * Copyright (c) 2015 Inocybe Technologies 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.ovsdb.southbound.transactions.md;
11 import static org.junit.Assert.assertEquals;
12 import static org.junit.Assert.assertNotNull;
13 import static org.junit.Assert.assertTrue;
14 import static org.mockito.Matchers.any;
15 import static org.mockito.Mockito.doNothing;
16 import static org.mockito.Mockito.doReturn;
17 import static org.mockito.Mockito.mock;
18 import static org.mockito.Mockito.verify;
19 import static org.mockito.Mockito.when;
20 import static org.powermock.reflect.Whitebox.getField;
22 import java.util.ArrayList;
23 import java.util.HashMap;
24 import java.util.List;
26 import java.util.concurrent.BlockingQueue;
27 import java.util.concurrent.ExecutorService;
28 import java.util.concurrent.LinkedBlockingQueue;
29 import java.util.concurrent.atomic.AtomicBoolean;
30 import org.junit.Before;
31 import org.junit.Test;
32 import org.junit.runner.RunWith;
33 import org.mockito.Mock;
34 import org.mockito.Mockito;
35 import org.mockito.junit.MockitoJUnitRunner;
36 import org.opendaylight.controller.md.sal.binding.api.BindingTransactionChain;
37 import org.opendaylight.controller.md.sal.binding.api.DataBroker;
38 import org.opendaylight.controller.md.sal.binding.api.ReadWriteTransaction;
39 import org.opendaylight.controller.md.sal.common.api.data.AsyncTransaction;
40 import org.opendaylight.controller.md.sal.common.api.data.TransactionChain;
41 import org.opendaylight.controller.md.sal.common.api.data.TransactionChainListener;
42 import org.powermock.reflect.Whitebox;
44 @RunWith(MockitoJUnitRunner.class)
45 public class TransactionInvokerImplTest {
47 private static final int QUEUE_SIZE = 10000;
48 @Mock private BindingTransactionChain chain;
49 @Mock private DataBroker db;
50 private final BlockingQueue<TransactionCommand> inputQueue = new LinkedBlockingQueue<>(QUEUE_SIZE);
51 private final BlockingQueue<ReadWriteTransaction> successfulTxQ
52 = new LinkedBlockingQueue<>(QUEUE_SIZE);
53 private final BlockingQueue<AsyncTransaction<?, ?>> failedTransactionQ
54 = new LinkedBlockingQueue<>(QUEUE_SIZE);
55 @Mock private ExecutorService executor;
56 @Mock private AtomicBoolean runTask;
57 private final Map<ReadWriteTransaction,TransactionCommand> transactionToCommand
59 private final List<ReadWriteTransaction> pendingTransactions = new ArrayList<>();
60 private TransactionInvokerImpl transactionInvokerImpl;
63 public void setUp() throws Exception {
64 transactionInvokerImpl = mock(TransactionInvokerImpl.class, Mockito.CALLS_REAL_METHODS);
65 getField(TransactionInvokerImpl.class, "chain").set(transactionInvokerImpl, chain);
66 getField(TransactionInvokerImpl.class, "db").set(transactionInvokerImpl, db);
70 public void testTransactionInvokerImpl() throws Exception {
71 getField(TransactionInvokerImpl.class, "inputQueue").set(transactionInvokerImpl, inputQueue);
72 when(db.createTransactionChain(any(TransactionChainListener.class)))
73 .thenReturn(mock(BindingTransactionChain.class));
74 TransactionInvokerImpl transactionInvokerImpl1 = new TransactionInvokerImpl(db);
75 verify(db).createTransactionChain(any(TransactionChainListener.class));
76 assertNotNull(Whitebox.getInternalState(transactionInvokerImpl1, "executor"));
80 public void testInvoke() throws Exception {
81 getField(TransactionInvokerImpl.class, "inputQueue").set(transactionInvokerImpl, inputQueue);
82 TransactionCommand command = mock(TransactionCommand.class);
83 transactionInvokerImpl.invoke(command);
84 BlockingQueue<TransactionCommand> testInputQueue = Whitebox.getInternalState(transactionInvokerImpl,
86 assertTrue(testInputQueue.contains(command));
90 public void testOnTransactionChainFailed() throws Exception {
91 getField(TransactionInvokerImpl.class, "failedTransactionQueue").set(transactionInvokerImpl,
93 AsyncTransaction<?, ?> transaction = mock(AsyncTransaction.class);
94 Throwable cause = mock(Throwable.class);
95 transactionInvokerImpl.onTransactionChainFailed(mock(TransactionChain.class), transaction, cause);
96 BlockingQueue<AsyncTransaction<?, ?>> testFailedTransactionQueue = Whitebox
97 .getInternalState(transactionInvokerImpl, "failedTransactionQueue");
98 assertTrue(testFailedTransactionQueue.contains(transaction));
101 @SuppressWarnings("rawtypes")
103 public void testExtractResubmitCommands() throws Exception {
104 AsyncTransaction<?, ?> transaction = mock(ReadWriteTransaction.class);
105 failedTransactionQ.put(transaction);
106 getField(TransactionInvokerImpl.class, "failedTransactionQueue").set(transactionInvokerImpl,
109 AsyncTransaction tx1 = mock(ReadWriteTransaction.class);
110 AsyncTransaction tx2 = mock(ReadWriteTransaction.class);
111 pendingTransactions.add((ReadWriteTransaction) tx1);
112 pendingTransactions.add((ReadWriteTransaction) transaction);
113 pendingTransactions.add((ReadWriteTransaction) tx2);
114 getField(TransactionInvokerImpl.class, "pendingTransactions").set(transactionInvokerImpl,
115 pendingTransactions);
117 List<ReadWriteTransaction> transactions = new ArrayList<>();
118 transactions.add((ReadWriteTransaction) tx1);
120 TransactionCommand txCommand = mock(TransactionCommand.class);
121 transactionToCommand.put((ReadWriteTransaction) tx1, txCommand);
122 transactionToCommand.put((ReadWriteTransaction) tx2, txCommand);
123 transactionToCommand.put((ReadWriteTransaction) transaction, txCommand);
124 getField(TransactionInvokerImpl.class, "transactionToCommand").set(transactionInvokerImpl,
125 transactionToCommand);
126 doNothing().when(transactionInvokerImpl).resetTransactionQueue();
128 List<TransactionCommand> testCommands = new ArrayList<>();
129 testCommands.add(txCommand);
131 assertEquals(testCommands, Whitebox.invokeMethod(transactionInvokerImpl, "extractResubmitCommands"));
135 public void testResetTransactionQueue() throws Exception {
136 doNothing().when(chain).close();
137 when(db.createTransactionChain(any(TransactionInvokerImpl.class))).thenReturn(chain);
139 failedTransactionQ.add(mock(AsyncTransaction.class));
140 getField(TransactionInvokerImpl.class, "pendingTransactions").set(transactionInvokerImpl, pendingTransactions);
141 getField(TransactionInvokerImpl.class, "transactionToCommand").set(transactionInvokerImpl,
142 transactionToCommand);
143 getField(TransactionInvokerImpl.class, "failedTransactionQueue").set(transactionInvokerImpl,
145 getField(TransactionInvokerImpl.class, "successfulTransactionQueue").set(transactionInvokerImpl, successfulTxQ);
147 Whitebox.invokeMethod(transactionInvokerImpl, "resetTransactionQueue");
148 assertNotNull(Whitebox.getInternalState(transactionInvokerImpl, "pendingTransactions"));
149 assertNotNull(Whitebox.getInternalState(transactionInvokerImpl, "transactionToCommand"));
150 BlockingQueue<AsyncTransaction<?, ?>> testFailedTransactionQueue = Whitebox
151 .getInternalState(transactionInvokerImpl, "failedTransactionQueue");
152 assertEquals(0, testFailedTransactionQueue.size());
156 public void testRecordPendingTransaction() throws Exception {
157 TransactionCommand command = mock(TransactionCommand.class);
158 ReadWriteTransaction transaction = mock(ReadWriteTransaction.class);
159 getField(TransactionInvokerImpl.class, "pendingTransactions").set(transactionInvokerImpl, pendingTransactions);
160 getField(TransactionInvokerImpl.class, "transactionToCommand").set(transactionInvokerImpl,
161 transactionToCommand);
162 Whitebox.invokeMethod(transactionInvokerImpl, "recordPendingTransaction", command, transaction);
164 List<ReadWriteTransaction> testPendingTransactions = Whitebox.getInternalState(transactionInvokerImpl,
165 "pendingTransactions");
166 assertEquals(1, testPendingTransactions.size());
168 Map<ReadWriteTransaction, TransactionCommand> testTransactionToCommand = Whitebox
169 .getInternalState(transactionInvokerImpl, "transactionToCommand");
170 assertEquals(1, testTransactionToCommand.size());
174 public void testExtractCommands() throws Exception {
175 List<TransactionCommand> commands = new ArrayList<>();
176 doReturn(commands).when(transactionInvokerImpl).extractResubmitCommands();
178 List<TransactionCommand> resubmitCommands = new ArrayList<>();
179 resubmitCommands.add(mock(TransactionCommand.class));
180 doReturn(resubmitCommands).when(transactionInvokerImpl).extractCommandsFromQueue();
182 List<TransactionCommand> testCommands = new ArrayList<>();
183 testCommands.addAll(resubmitCommands);
185 assertEquals(testCommands, Whitebox.invokeMethod(transactionInvokerImpl, "extractCommands"));
189 public void testExtractCommandsFromQueue() throws Exception {
190 TransactionCommand command = mock(TransactionCommand.class);
191 inputQueue.add(command);
192 getField(TransactionInvokerImpl.class, "inputQueue").set(transactionInvokerImpl, inputQueue);
193 List<TransactionCommand> testResult = new ArrayList<>();
194 testResult.add(command);
195 assertEquals(testResult, Whitebox.invokeMethod(transactionInvokerImpl, "extractCommandsFromQueue"));
199 public void testForgetSuccessfulTransactions() throws Exception {
200 ReadWriteTransaction transaction = mock(ReadWriteTransaction.class);
201 successfulTxQ.add(transaction);
202 pendingTransactions.add(transaction);
203 transactionToCommand.put(transaction, mock(TransactionCommand.class));
204 getField(TransactionInvokerImpl.class, "successfulTransactionQueue").set(transactionInvokerImpl, successfulTxQ);
205 getField(TransactionInvokerImpl.class, "pendingTransactions").set(transactionInvokerImpl, pendingTransactions);
206 getField(TransactionInvokerImpl.class, "transactionToCommand").set(transactionInvokerImpl,
207 transactionToCommand);
209 Whitebox.invokeMethod(transactionInvokerImpl, "forgetSuccessfulTransactions");
211 List<ReadWriteTransaction> testPendingTransactions = Whitebox.getInternalState(transactionInvokerImpl,
212 "pendingTransactions");
213 Map<ReadWriteTransaction, TransactionCommand> testTransactionToCommand = Whitebox
214 .getInternalState(transactionInvokerImpl, "transactionToCommand");
215 assertTrue(testPendingTransactions.isEmpty());
216 assertTrue(testTransactionToCommand.isEmpty());
220 public void testClose() throws Exception {
221 getField(TransactionInvokerImpl.class, "executor").set(transactionInvokerImpl, executor);
222 getField(TransactionInvokerImpl.class, "runTask").set(transactionInvokerImpl, runTask);
223 doNothing().when(executor).shutdown();
224 transactionInvokerImpl.close();
225 verify(executor).shutdown();