1 /* 2 * Copyright (C) 2017 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License 15 */ 16 17 package com.android.compatibility.common.util; 18 19 import static junit.framework.Assert.assertEquals; 20 import static junit.framework.Assert.assertFalse; 21 import static junit.framework.Assert.assertTrue; 22 import static junit.framework.Assert.fail; 23 import static org.junit.Assume.assumeTrue; 24 25 import com.android.tradefed.build.IBuildInfo; 26 import com.android.tradefed.device.ITestDevice; 27 28 import org.easymock.EasyMock; 29 import org.junit.AssumptionViolatedException; 30 import org.junit.Before; 31 import org.junit.Ignore; 32 import org.junit.Test; 33 import org.junit.runner.RunWith; 34 import org.junit.runners.JUnit4; 35 36 import java.util.ArrayList; 37 import java.util.Arrays; 38 import java.util.List; 39 40 import junit.framework.AssertionFailedError; 41 42 /** 43 * Tests for {@link BusinessLogicHostExecutor}. 44 */ 45 @RunWith(JUnit4.class) 46 public class BusinessLogicHostExecutorTest { 47 48 private static final String THIS_CLASS = 49 "com.android.compatibility.common.util.BusinessLogicHostExecutorTest"; 50 private static final String METHOD_1 = THIS_CLASS + ".method1"; 51 private static final String METHOD_2 = THIS_CLASS + ".method2"; 52 private static final String METHOD_3 = THIS_CLASS + ".method3"; 53 private static final String METHOD_4 = THIS_CLASS + ".method4"; 54 private static final String METHOD_5 = THIS_CLASS + ".method5"; 55 private static final String METHOD_6 = THIS_CLASS + ".method6"; 56 private static final String METHOD_7 = THIS_CLASS + ".method7"; 57 private static final String METHOD_8 = THIS_CLASS + ".method8"; 58 private static final String METHOD_9 = THIS_CLASS + ".method9"; 59 private static final String METHOD_10 = THIS_CLASS + ".method10"; 60 private static final String FAKE_METHOD = THIS_CLASS + ".methodDoesntExist"; 61 private static final String ARG_STRING_1 = "arg1"; 62 private static final String ARG_STRING_2 = "arg2"; 63 64 private static final String OTHER_METHOD_1 = THIS_CLASS + "$OtherClass.method1"; 65 66 private String mInvoked = null; 67 private Object[] mArgsUsed = null; 68 private IBuildInfo mMockBuild; 69 private ITestDevice mMockDevice; 70 private BusinessLogicExecutor mExecutor; 71 72 @Before setUp()73 public void setUp() { 74 mMockBuild = EasyMock.createMock(IBuildInfo.class); 75 mMockDevice = EasyMock.createMock(ITestDevice.class); 76 mExecutor = new BusinessLogicHostExecutor(mMockDevice, mMockBuild, this); 77 // reset the instance variables tracking the method invoked and the args used 78 mInvoked = null; 79 mArgsUsed = null; 80 // reset the OtherClass class variable tracking the method invoked 81 OtherClass.otherInvoked = null; 82 } 83 84 @Test testInvokeMethodInThisClass()85 public void testInvokeMethodInThisClass() throws Exception { 86 mExecutor.invokeMethod(METHOD_1); 87 // assert that mInvoked was set for this BusinessLogicDeviceExecutorTest instance 88 assertEquals("Failed to invoke method in this class", mInvoked, METHOD_1); 89 } 90 91 @Test testInvokeMethodInOtherClass()92 public void testInvokeMethodInOtherClass() throws Exception { 93 mExecutor.invokeMethod(OTHER_METHOD_1); 94 // assert that OtherClass.method1 was invoked, and static field of OtherClass was changed 95 assertEquals("Failed to invoke method in other class", OtherClass.otherInvoked, 96 OTHER_METHOD_1); 97 } 98 99 @Test testInvokeMethodWithStringArgs()100 public void testInvokeMethodWithStringArgs() throws Exception { 101 mExecutor.invokeMethod(METHOD_2, ARG_STRING_1, ARG_STRING_2); 102 assertEquals("Failed to invoke method in this class", mInvoked, METHOD_2); 103 // assert both String arguments were correctly set for method2 104 assertEquals("Failed to set first argument", mArgsUsed[0], ARG_STRING_1); 105 assertEquals("Failed to set second argument", mArgsUsed[1], ARG_STRING_2); 106 } 107 108 @Test testInvokeMethodWithStringAndDeviceArgs()109 public void testInvokeMethodWithStringAndDeviceArgs() throws Exception { 110 mExecutor.invokeMethod(METHOD_3, ARG_STRING_1); 111 assertEquals("Failed to invoke method in this class", mInvoked, METHOD_3); 112 // assert that String arg and ITestDevice arg were correctly set for method3 113 assertEquals("Failed to set first argument", mArgsUsed[0], ARG_STRING_1); 114 assertEquals("Failed to set second argument", mArgsUsed[1], mMockDevice); 115 } 116 117 @Test testInvokeMethodWithDeviceAndStringArgs()118 public void testInvokeMethodWithDeviceAndStringArgs() throws Exception { 119 mExecutor.invokeMethod(METHOD_4, ARG_STRING_1); 120 assertEquals("Failed to invoke method in this class", mInvoked, METHOD_4); 121 // Like testInvokeMethodWithStringAndDeviceArgs, but flip the args for method4 122 assertEquals("Failed to set first argument", mArgsUsed[0], mMockDevice); 123 assertEquals("Failed to set second argument", mArgsUsed[1], ARG_STRING_1); 124 } 125 126 @Test testInvokeMethodWithStringArrayArg()127 public void testInvokeMethodWithStringArrayArg() throws Exception { 128 mExecutor.invokeMethod(METHOD_5, ARG_STRING_1, ARG_STRING_2); 129 assertEquals("Failed to invoke method in this class", mInvoked, METHOD_5); 130 // assert both String arguments were correctly set for method5 131 assertEquals("Failed to set first argument", mArgsUsed[0], ARG_STRING_1); 132 assertEquals("Failed to set second argument", mArgsUsed[1], ARG_STRING_2); 133 } 134 135 @Test testInvokeMethodWithEmptyStringArrayArg()136 public void testInvokeMethodWithEmptyStringArrayArg() throws Exception { 137 mExecutor.invokeMethod(METHOD_5); 138 assertEquals("Failed to invoke method in this class", mInvoked, METHOD_5); 139 // assert no String arguments were set for method5 140 assertEquals("Incorrectly set args", mArgsUsed.length, 0); 141 } 142 143 @Test testInvokeMethodWithStringAndStringArrayArgs()144 public void testInvokeMethodWithStringAndStringArrayArgs() throws Exception { 145 mExecutor.invokeMethod(METHOD_6, ARG_STRING_1, ARG_STRING_2); 146 assertEquals("Failed to invoke method in this class", mInvoked, METHOD_6); 147 // assert both String arguments were correctly set for method6 148 assertEquals("Failed to set first argument", mArgsUsed[0], ARG_STRING_1); 149 assertEquals("Failed to set second argument", mArgsUsed[1], ARG_STRING_2); 150 } 151 152 @Test testInvokeMethodWithAllArgTypes()153 public void testInvokeMethodWithAllArgTypes() throws Exception { 154 mExecutor.invokeMethod(METHOD_7, ARG_STRING_1, ARG_STRING_2); 155 assertEquals("Failed to invoke method in this class", mInvoked, METHOD_7); 156 // assert all arguments were correctly set for method7 157 assertEquals("Failed to set first argument", mArgsUsed[0], ARG_STRING_1); 158 assertEquals("Failed to set second argument", mArgsUsed[1], mMockBuild); 159 assertEquals("Failed to set second argument", mArgsUsed[2], mMockDevice); 160 assertEquals("Failed to set third argument", mArgsUsed[3], ARG_STRING_2); 161 } 162 163 @Test testInvokeOverloadedMethodOneArg()164 public void testInvokeOverloadedMethodOneArg() throws Exception { 165 mExecutor.invokeMethod(METHOD_1, ARG_STRING_1); 166 assertEquals("Failed to invoke method in this class", mInvoked, METHOD_1); 167 assertEquals("Set wrong number of arguments", mArgsUsed.length, 1); 168 assertEquals("Failed to set first argument", mArgsUsed[0], ARG_STRING_1); 169 } 170 171 @Test testInvokeOverloadedMethodTwoArgs()172 public void testInvokeOverloadedMethodTwoArgs() throws Exception { 173 mExecutor.invokeMethod(METHOD_1, ARG_STRING_1, ARG_STRING_2); 174 assertEquals("Failed to invoke method in this class", mInvoked, METHOD_1); 175 assertEquals("Set wrong number of arguments", mArgsUsed.length, 2); 176 assertEquals("Failed to set first argument", mArgsUsed[0], ARG_STRING_1); 177 assertEquals("Failed to set second argument", mArgsUsed[1], ARG_STRING_2); 178 } 179 180 @Test(expected = RuntimeException.class) testInvokeNonExistentMethod()181 public void testInvokeNonExistentMethod() throws Exception { 182 mExecutor.invokeMethod(FAKE_METHOD, ARG_STRING_1, ARG_STRING_2); 183 } 184 185 @Test(expected = RuntimeException.class) testInvokeMethodTooManyArgs()186 public void testInvokeMethodTooManyArgs() throws Exception { 187 mExecutor.invokeMethod(METHOD_3, ARG_STRING_1, ARG_STRING_2); 188 } 189 190 @Test(expected = RuntimeException.class) testInvokeMethodTooFewArgs()191 public void testInvokeMethodTooFewArgs() throws Exception { 192 mExecutor.invokeMethod(METHOD_2, ARG_STRING_1); 193 } 194 195 @Test(expected = RuntimeException.class) testInvokeMethodIncompatibleArgs()196 public void testInvokeMethodIncompatibleArgs() throws Exception { 197 mExecutor.invokeMethod(METHOD_8, ARG_STRING_1); 198 } 199 200 @Test testExecuteConditionCheckReturnValue()201 public void testExecuteConditionCheckReturnValue() throws Exception { 202 assertTrue("Wrong return value", 203 mExecutor.executeCondition(METHOD_2, ARG_STRING_1, ARG_STRING_1)); 204 assertFalse("Wrong return value", 205 mExecutor.executeCondition(METHOD_2, ARG_STRING_1, ARG_STRING_2)); 206 } 207 208 @Test(expected = RuntimeException.class) testExecuteInvalidCondition()209 public void testExecuteInvalidCondition() throws Exception { 210 mExecutor.executeCondition(METHOD_1); // method1 does not return type boolean 211 } 212 213 @Test testExecuteAction()214 public void testExecuteAction() throws Exception { 215 mExecutor.executeAction(METHOD_2, ARG_STRING_1, ARG_STRING_2); 216 assertEquals("Failed to invoke method in this class", mInvoked, METHOD_2); 217 // assert both String arguments were correctly set for method2 218 assertEquals("Failed to set first argument", mArgsUsed[0], ARG_STRING_1); 219 assertEquals("Failed to set second argument", mArgsUsed[1], ARG_STRING_2); 220 } 221 222 @Test(expected = RuntimeException.class) testExecuteActionThrowException()223 public void testExecuteActionThrowException() throws Exception { 224 mExecutor.executeAction(METHOD_9); 225 } 226 227 @Test testExecuteActionViolateAssumption()228 public void testExecuteActionViolateAssumption() throws Exception { 229 try { 230 mExecutor.executeAction(METHOD_10); 231 // JUnit4 doesn't support expecting AssumptionViolatedException with "expected" 232 // attribute on @Test annotation, so test using Assert.fail() 233 fail("Expected assumption failure"); 234 } catch (AssumptionViolatedException e) { 235 // expected 236 } 237 } 238 method1()239 public void method1() { 240 mInvoked = METHOD_1; 241 } 242 243 // overloaded method with one arg method1(String arg1)244 public void method1(String arg1) { 245 mInvoked = METHOD_1; 246 mArgsUsed = new Object[]{arg1}; 247 } 248 249 // overloaded method with two args method1(String arg1, String arg2)250 public void method1(String arg1, String arg2) { 251 mInvoked = METHOD_1; 252 mArgsUsed = new Object[]{arg1, arg2}; 253 } 254 method2(String arg1, String arg2)255 public boolean method2(String arg1, String arg2) { 256 mInvoked = METHOD_2; 257 mArgsUsed = new Object[]{arg1, arg2}; 258 return arg1.equals(arg2); 259 } 260 method3(String arg1, ITestDevice arg2)261 public void method3(String arg1, ITestDevice arg2) { 262 mInvoked = METHOD_3; 263 264 mArgsUsed = new Object[]{arg1, arg2}; 265 } 266 267 // Same as method3, but flipped args method4(ITestDevice arg1, String arg2)268 public void method4(ITestDevice arg1, String arg2) { 269 mInvoked = METHOD_4; 270 mArgsUsed = new Object[]{arg1, arg2}; 271 } 272 method5(String... args)273 public void method5(String... args) { 274 mInvoked = METHOD_5; 275 mArgsUsed = args; 276 } 277 method6(String arg1, String... moreArgs)278 public void method6(String arg1, String... moreArgs) { 279 mInvoked = METHOD_6; 280 List<String> allArgs = new ArrayList<>(); 281 allArgs.add(arg1); 282 allArgs.addAll(Arrays.asList(moreArgs)); 283 mArgsUsed = allArgs.toArray(new String[0]); 284 } 285 method7(String arg1, IBuildInfo arg2, ITestDevice arg3, String... moreArgs)286 public void method7(String arg1, IBuildInfo arg2, ITestDevice arg3, String... moreArgs) { 287 mInvoked = METHOD_7; 288 List<Object> allArgs = new ArrayList<>(); 289 allArgs.add(arg1); 290 allArgs.add(arg2); 291 allArgs.add(arg3); 292 allArgs.addAll(Arrays.asList(moreArgs)); 293 mArgsUsed = allArgs.toArray(new Object[0]); 294 } 295 method8(String arg1, Integer arg2)296 public void method8(String arg1, Integer arg2) { 297 // This method should never be successfully invoked, since Integer parameter types are 298 // unsupported for the BusinessLogic service 299 } 300 301 // throw AssertionFailedError 302 @Ignore method9()303 public void method9() throws AssertionFailedError { 304 assertTrue(false); 305 } 306 307 // throw AssumptionViolatedException method10()308 public void method10() throws AssumptionViolatedException { 309 assumeTrue(false); 310 } 311 312 public static class OtherClass { 313 314 public static String otherInvoked = null; 315 method1()316 public void method1() { 317 otherInvoked = OTHER_METHOD_1; 318 } 319 } 320 } 321