View Javadoc

1   package cz.cuni.amis.pogamut.emohawk.bot;
2   
3   import java.util.concurrent.TimeUnit;
4   
5   import cz.cuni.amis.pogamut.emohawk.test.EmohawkTest;
6   import cz.cuni.amis.pogamut.emohawk.utils.UCCWrapperConfEmohawk;
7   import cz.cuni.amis.pogamut.ut2004.bot.impl.UT2004Bot;
8   import cz.cuni.amis.pogamut.ut2004.bot.params.UT2004BotParameters;
9   import cz.cuni.amis.pogamut.ut2004.server.exception.UCCStartException;
10  import cz.cuni.amis.utils.StopWatch;
11  
12  /**
13   * UT2004Bot test - it allows you to easily specify the game type and map name the bot should run 
14   * at + specify a timeout for the test.
15   * <p><p>
16   * Just use one of the {@link EmohawkBotTest#startTest(Class)} methods 
17   * 
18   * @author Jimmy
19   */
20  public abstract class EmohawkBotTest extends EmohawkTest {
21  
22  	/**
23       * Starts UCC server according to params obtained from {@link EmohawkBotTest#getGameType()} and
24       * {@link EmohawkBotTest#getMapName()}.
25       *
26       * @throws cz.cuni.amis.pogamut.ut2004.server.exceptions.UCCStartException
27       */
28      @Override
29  	public void startUCC(UCCWrapperConfEmohawk uccConf) throws UCCStartException {
30          uccConf.setMapName(getMapName());
31          super.startUCC(uccConf);
32      }
33      
34      /**
35       * @return the map the UCC should load for the test
36       */
37      protected String getMapName() {
38      	return "EmohawkVille_Runtime_04";
39      }
40      
41      /**
42       * Starts the test.
43       * <p><p>
44       * Test bot will be controlled by 'controllerClass'.
45       * <p><p>
46       * The test will timeout after 1 minutes.
47       * 
48       * @param controllerClass
49       */
50      protected void startTest(Class<? extends EmohawkBotTestController> controllerClass) {
51  		startTest(controllerClass, 1);
52      }
53          
54      /**
55       * Starts the test.
56       * <p><p>
57       * Test bot will be controlled by 'controllerClass'.
58       * <p><p>
59       * The test will timeout after 'latchWaitMinutes'.
60       * 
61       * @param controllerClass
62       * @param latchWaitMinutes
63       */
64  	protected void startTest(Class<? extends EmohawkBotTestController> controllerClass, double latchWaitMinutes) {
65      	startTest(controllerClass, latchWaitMinutes, null);
66  	}
67  	
68  	/**
69       * Starts the test.
70       * <p><p>
71       * Test bot will be controlled by 'controllerClass'.
72       * <p><p>
73       * The test will timeout after 'latchWaitMinutes'.
74       * <p><p>
75       * The test will lauch 'agentsCount' of bots of 'controllerClass' creating empty {@link UT2004BotParameters} for every one of them.
76       * 
77       * @param controllerClass
78       * @param latchWaitMinutes
79       * @param agentsCount
80       */
81  	protected void startTest(Class<? extends EmohawkBotTestController> controllerClass, double latchWaitMinutes, int agentsCount) {
82  		UT2004BotParameters[] params = new UT2004BotParameters[agentsCount];
83  		for (int i = 0; i < agentsCount; ++i) {
84  			params[i] = new UT2004BotParameters();
85  		}
86      	startTest(controllerClass, latchWaitMinutes, params);
87  	}
88  	
89  	/**
90  	 * Starts the test.
91       * <p><p>
92       * Test bot will be controlled by 'controllerClass' and will be configured with 'params.
93       * <p><p>
94       * The test will timeout after 'latchWaitMinutes'.
95       * 
96       * TODO: [Jimmy] in the case of more bots, we should hook listeners to failure flags of bots to end the test case as early as possible
97       * 
98  	 * @param controllerClass
99  	 * @param params
100 	 * @param latchWaitMinutes
101 	 */
102     protected void startTest(Class<? extends EmohawkBotTestController> controllerClass, double latchWaitMinutes, UT2004BotParameters... params) {
103     	int numParams = (params == null || params.length == 0 ? 0 : params.length);
104     	int numBots = numParams == 0 ? 1 : numParams;
105     	
106     	UT2004Bot bots[];
107     	
108     	if (params == null || params.length == 0) {
109     		bots = new UT2004Bot[1];
110     		bots[0] = startUTBot(controllerClass);
111     	} else {
112     		bots = startAllUTBots(controllerClass, params).toArray(new UT2004Bot[0]);
113     	}
114     	
115     	long timeoutInMillis = (long)(latchWaitMinutes * 60 * 1000);
116     	
117     	StopWatch watches = new StopWatch();
118     	
119     	for (int i = 0; i < numBots; ++i) {
120     		EmohawkBotTestController controller = (EmohawkBotTestController) bots[i].getController();
121     		try {
122     			controller.getTestLatch().await((long)(timeoutInMillis - watches.check()), TimeUnit.MILLISECONDS);
123     		} catch (Exception ex) {
124     			ex.printStackTrace();
125     			for (int j = i; j < numBots; ++j) bots[j].kill();
126     			Throwable throwable = controller.getLogicModule().getLogicException();
127     			throw new RuntimeException("Test failed, bot did not finished.", throwable);
128     		}
129     		if (timeoutInMillis - watches.check() < 0) {
130     			controller.timeout();
131     		}
132     		bots[i].kill();
133     		if (controller.isFailure()) {
134     			for (int j = i+1; j < numBots; ++j) bots[j].kill();
135     			if (controller.getMessage() != null) {
136     				System.out.println("[ERROR] " + controller.getMessage());
137     			}
138     			
139 				String exceptionMessage = "Test has failed!";
140     			if(controller.getMessage() == null)
141     				exceptionMessage += " " + controller.getMessage();
142 				throw new RuntimeException(exceptionMessage, controller.getCause());
143     			
144     		} else {
145     			if (controller.getMessage() != null) {
146     				System.out.println("[OK] " + controller.getMessage());
147     			}
148     		}
149     	}
150     	
151     	System.out.println("---/// TEST OK ///---");    	
152 	}
153  
154 }