OPNFLWPLUG-1032: Neon-MRI: Bump odlparent, yangtools, mdsal
[openflowplugin.git] / samples / simple-client / src / main / java / org / opendaylight / openflowjava / protocol / impl / clients / ScenarioHandler.java
1 /*
2  * Copyright (c) 2013 Pantheon Technologies s.r.o. 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
9 package org.opendaylight.openflowjava.protocol.impl.clients;
10
11 import io.netty.channel.ChannelHandlerContext;
12 import java.util.Deque;
13 import java.util.concurrent.BlockingQueue;
14 import java.util.concurrent.LinkedBlockingQueue;
15 import java.util.concurrent.TimeUnit;
16 import org.slf4j.Logger;
17 import org.slf4j.LoggerFactory;
18
19 /**
20  * Scenario handler thread.
21  *
22  * @author michal.polkorab
23  */
24 public class ScenarioHandler extends Thread {
25
26     private static final Logger LOG = LoggerFactory.getLogger(ScenarioHandler.class);
27     private Deque<ClientEvent> scenario;
28     private final BlockingQueue<byte[]> ofMsg;
29     private ChannelHandlerContext ctx;
30     private int eventNumber;
31     private volatile boolean scenarioFinished = false;
32     private int freeze = 2;
33     private long sleepBetweenTries = 100L;
34     private boolean finishedOK = true;
35
36     /**
37      * Constructor.
38      *
39      * @param scenario {@link Deque}
40      */
41     public ScenarioHandler(Deque<ClientEvent> scenario) {
42         this.scenario = scenario;
43         ofMsg = new LinkedBlockingQueue<>();
44     }
45
46     public ScenarioHandler(Deque<ClientEvent> scenario, int freeze, long sleepBetweenTries) {
47         this.scenario = scenario;
48         ofMsg = new LinkedBlockingQueue<>();
49         this.sleepBetweenTries = sleepBetweenTries;
50         this.freeze = freeze;
51     }
52
53     @Override
54     public void run() {
55         int freezeCounter = 0;
56         while (!scenario.isEmpty()) {
57             LOG.debug("Running event #{}", eventNumber);
58             ClientEvent peek = scenario.peekLast();
59             if (peek instanceof WaitForMessageEvent) {
60                 LOG.debug("WaitForMessageEvent");
61                 try {
62                     WaitForMessageEvent event = (WaitForMessageEvent) peek;
63                     event.setHeaderReceived(ofMsg.poll(2000, TimeUnit.MILLISECONDS));
64                 } catch (InterruptedException e) {
65                     LOG.error("Error {}", e);
66                     break;
67                 }
68             } else if (peek instanceof SendEvent) {
69                 LOG.debug("Proceed - sendevent");
70                 SendEvent event = (SendEvent) peek;
71                 event.setCtx(ctx);
72             }
73             if (peek.eventExecuted()) {
74                 LOG.info("Scenario step finished OK, moving to next step.");
75                 scenario.removeLast();
76                 eventNumber++;
77                 freezeCounter = 0;
78                 finishedOK = true;
79             } else {
80                 freezeCounter++;
81             }
82             if (freezeCounter > freeze) {
83                 LOG.warn("Scenario frozen: {}", freezeCounter);
84                 LOG.warn("Scenario step not finished NOT OK! {}", freezeCounter);
85                 this.finishedOK = false;
86                 break;
87             }
88             try {
89                 sleep(sleepBetweenTries);
90             } catch (InterruptedException e) {
91                 LOG.error("Error {}", e);
92             }
93         }
94         LOG.debug("Scenario finished");
95         synchronized (this) {
96             scenarioFinished = true;
97             this.notifyAll();
98         }
99     }
100
101     /**
102      * Returns true if scenario is done / empty.
103      */
104     public boolean isEmpty() {
105         return scenario.isEmpty();
106     }
107
108     /**
109      * Returns the scenario.
110      */
111     public Deque<ClientEvent> getScenario() {
112         return scenario;
113     }
114
115     /**
116      * Sets the scenario.
117      *
118      * @param scenario scenario filled with desired events
119      */
120     public void setScenario(Deque<ClientEvent> scenario) {
121         this.scenario = scenario;
122     }
123
124     /**
125      * Sets the ChannelHandlerContext.
126      *
127      * @param ctx context which will be used for sending messages (SendEvents)
128      */
129     public void setCtx(ChannelHandlerContext ctx) {
130         this.ctx = ctx;
131     }
132
133     /**
134      * Adds a message.
135      *
136      * @param message received message that is compared to expected message
137      */
138     public void addOfMsg(byte[] message) {
139         ofMsg.add(message);
140     }
141
142     /**
143      * Returns true is scenario is finished.
144      */
145     public boolean isScenarioFinished() {
146         return scenarioFinished;
147     }
148
149     public boolean isFinishedOK() {
150         return finishedOK;
151     }
152 }