Slide 1

Slide 1 text

Automated Testing Dimitris K.

Slide 2

Slide 2 text

Quality Brand Automated Testing

Slide 3

Slide 3 text

Automated Testing Extremely important to us

Slide 4

Slide 4 text

Quality Yesterday Automated Testing

Slide 5

Slide 5 text

Quality Yesterday Manual Testing Automated Testing

Slide 6

Slide 6 text

Unit Testing Quality Yesterday Automated Testing

Slide 7

Slide 7 text

Quality Yesterday “Add ability to compile and run tests” - Eric Burke Automated Testing

Slide 8

Slide 8 text

Quality Today Automated Testing

Slide 9

Slide 9 text

No Flakiness Quality Today Automated Testing

Slide 10

Slide 10 text

Easy to write tests Quality Today Automated Testing

Slide 11

Slide 11 text

Catch edge cases Quality Today Automated Testing

Slide 12

Slide 12 text

Quality Today Automated Testing Graybox testing is preferred

Slide 13

Slide 13 text

Quality Today Automated Testing Tests are red == master is red

Slide 14

Slide 14 text

Robots Automated Testing

Slide 15

Slide 15 text

Robots Thin layer above UI framework Automated Testing Fluent API Single point to update your code

Slide 16

Slide 16 text

Robots public class InvoiceScreenRobot extends ScreenRobot { public InvoiceScreenRobot typeTitle(String title) { onView(withId(R.id.title)).perform(typeText(title)); return this; } // More here... public void clickSend() { onView(withId(R.id.send)).perform(click()); } } Automated Testing

Slide 17

Slide 17 text

Robots public void testSendInvoice() { withRobot(InvoiceScreenRobot.class) // .typeTitle("Sample Title") // .typeNumber("#000001") // .typeName("Square User") // .typeEmail("[email protected]") // .clickSend(); } Automated Testing

Slide 18

Slide 18 text

Robots public void testSendInvoice() { withRobot(InvoiceScreenRobot.class) // .checkIsDisabled(R.id.send) // .typeTitle("Sample Title") // .typeNumber("#000001") // .typeName("Square User") // .typeEmail("[email protected]") // .checkIsEnabled(R.id.send) // .clickSend(); } Automated Testing

Slide 19

Slide 19 text

Mock Mode Automated Testing

Slide 20

Slide 20 text

Mock Mode Eliminate network flakiness Automated Testing Rapid development Test network edge cases

Slide 21

Slide 21 text

Mock Mode @Provides @Singleton MyService provideMyService(RestAdapter adapter) { return adapter.create(MyService.class); } Automated Testing

Slide 22

Slide 22 text

Mock Mode @Provides @Singleton MyService provideMyService(RestAdapter adapter) { MyService real = restAdapter.create(MyService.class); MyService mock = new MockMyService(); return ServiceProxy.newInstance(MyService.class, mock, real); } Automated Testing

Slide 23

Slide 23 text

Mock Mode public class ServiceProxy implements InvocationHandler { @Override public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { Object service = mockModeOn() ? mock : real; try { return method.invoke(service, args); } catch (InvocationTargetException e) { throw e.getTargetException(); } } Automated Testing

Slide 24

Slide 24 text

Mock Mode public class MockMyService implements MyService { @Override public Response doSomething(Request request) { delay(); boolean success = true; return new Response(success); } } Automated Testing

Slide 25

Slide 25 text

Test Matrix Automated Testing

Slide 26

Slide 26 text

Test Matrix Automated Testing Card Not Present Flow

Slide 27

Slide 27 text

Test Matrix 7 card types Automated Testing 4 languages 4 receipt types

Slide 28

Slide 28 text

Test Matrix Automated Testing 112 tests to write

Slide 29

Slide 29 text

Burst Automated Testing

Slide 30

Slide 30 text

Burst Test Generator Automated Testing

Slide 31

Slide 31 text

Burst Variation Proximity Automated Testing

Slide 32

Slide 32 text

Burst Type Safety Automated Testing

Slide 33

Slide 33 text

Burst Use Everywhere Automated Testing

Slide 34

Slide 34 text

Burst Automated Testing Not @Parameterized.Parameters(name = "{0}") public static List parameters() { return Arrays.asList(new Object[] { new Factory() { @Override public BufferedSink create(Buffer data) { return data; } @Override public String toString() { return "Buffer"; } }, }, new Object[] { new Factory() { @Override public BufferedSink create(Buffer data) { return new RealBufferedSink(data); } @Override public String toString() { return "RealBufferedSink"; } } }); } @Parameterized.Parameter public Factory factory;

Slide 35

Slide 35 text

Burst public enum Soda { COKE, PEPSI, RC_COLA } @RunWith(BurstJUnit4.class) public class SampleTest { @Test public void sodas(Soda soda) { // Test will run 3 times assertNotNull(soda); } } Automated Testing

Slide 36

Slide 36 text

Burst public enum Soda { COKE, PEPSI, RC_COLA } @RunWith(BurstJUnit4.class) public class SampleTest { @Test public void sodasAndSnacks(Soda soda, Snack snack) { // Test will run 9 times assertNotNull(soda); assertNotNull(snack); } } public enum Snack { CHIPS, KITKAT, CANDY } Automated Testing

Slide 37

Slide 37 text

Burst Friendly Test Naming Automated Testing

Slide 38

Slide 38 text

Burst sodasAndSnacks[Soda.COKE, Snack.CHIPS] sodasAndSnacks[Soda.COKE, Snack.KITKAT] sodasAndSnacks[Soda.COKE, Snack.CANDY] Automated Testing

Slide 39

Slide 39 text

Burst @TabletOnly public void testTabletFeature() { // This test will only be executed on tablets. } Automated Testing

Slide 40

Slide 40 text

Burst @TabletOnly public void testTabletFeature() { // This test will only be executed on tablets. } @PhoneOnly public void testPhoneFeature() { // This test will only be executed on phones. } Automated Testing

Slide 41

Slide 41 text

Automated Testing @TabletOnly public void testTipBringsAmountOver25() { loginAsAndStartActivity("bart"); performAuthSteps(2499L); // Tip withRobot(TipScreenRobot.class).clickTipOptionOne(); // Sign withRobot(SignScreenRobot.class) .performSign() .clickContinue(); // Receipt withRobot(ReceiptScreenRobot.class) .performEmailReceipt("[email protected]") .clickNewSale(); }

Slide 42

Slide 42 text

Tips Automated Testing

Slide 43

Slide 43 text

Tips Animations OFF Automated Testing

Slide 44

Slide 44 text

Don’t Sleep() Tips Automated Testing

Slide 45

Slide 45 text

Tips Screenshots Automated Testing

Slide 46

Slide 46 text

Tips Automated Testing @Override protected void setUp() throws Exception { super.setUp(); setFailureHandler(new RegisterFailureHandler(this)); }

Slide 47

Slide 47 text

Tips Automated Testing public class RegisterFailureHandler implements FailureHandler { private final TestCase testCase; public RegisterFailureHandler(TestCase testCase) { this.testCase = testCase; } @Override public void handle(Throwable throwable, Matcher viewMatcher) { // Very useful for finding out what went wrong... takeAndUploadScreenshot(testCase.getName()); // Delegate to real failure handler here. } }

Slide 48

Slide 48 text

Tips Automated Testing public class ScreenShotProxy implements InvocationHandler { @Override public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { try { Object result = method.invoke(proxy, args); takeScreenShot(); // <----- magic. return result; } catch (InvocationTargetException e) { throw e.getTargetException(); } } }

Slide 49

Slide 49 text

Tips Keyboard :( Automated Testing

Slide 50

Slide 50 text

A https://github.com/square/burst https://squareup.com/careers https://github.com/square/burst