Tests: Not just the thing you did in school
- What is Testing To You?
- Ensuring code does what it is meant to do
- Ensuring system works as expected
- Being able to manually test things
- What is your current testing strategy?
- Code and hope it works?
- Code locally, test, push to production and retest?
- Staging Environments?
- Are you confident in your build?
TDD: Test Driven Development
Write test
Write code
Refactor
BDD: Behaviour Driven Development
-
Philosophy / Definition
- Focuses on clear understanding of software behavior from stakeholders
- Focuses on why code should be created: thinking "from the outside in"
- Extends TDD: tests written in natural language that non-programmers can read
- Can be used as Acceptance Tests
Different types of tests
- There are many but will focus on 3
- Unit Tests
- Testing core unit of works
- Isolated: no interaction with other systems (e.g. databases, web services)
- Integration Tests
- Test the integration between 2 different "units" / systems (e.g. your core system and the database / web service)
- Database interaction: test database or in-memory databses (H2 / SQLite)
- Functional Tests
Where to Start?
Functional Tests
Integration Tests
Unit Tests
Big picture
Small picture
More Complex
Simple
Less Robust
Robust
Slow
Fast
Test Suites / Frameworks
-
Unit & Integration Testing
-
BDD specific
Structure of Testing Frameworks
Setup (before all / BeforeClass)
Runs once before any tests have run
Create DB schema
Teardown (after all / AfterClass)
Runs once after all tests are run
Drop DB schema
Test (Test Fixture)
Actual test to run
Assert something
Test Fixture Setup (before each)
Runs each time before any test (i.e. runs 2 times if there are 2 tests)
Populate DB / state
Test Fixture Teardown (after each)
Runs each time after any test
Clear DB / state
Structure of Testing Functions
Setup (before all / BeforeClass)
- Runs once before any tests have run
- E.g. create database schema
Test Fixture Setup (before each)
- Runs each time before any test
- E.g. clear & populate database / state
Test (Test Fixture)
- Actual test to run: Assert something
Test Fixture Teardown (after each)
- Runs each time after any test
- E.g. clear database / state
Teardown (after all / AfterClass)
- Runs once after all tests are run
- E.g. drop database schema
Testing Concepts (1/3)
- Test (Test Fixture)
- Actual test to run
- Assert something
@Test
addTwoPositiveNumbers(){
calc = new Calculator();
output = calc.add(1,2);
Assert.Equal(3, output);
}
@Test
primeNumberIsCorrectlyDetected(){
calc = new Calculator();
output = calc.isPrime(2);
Assert.IsTrue(output);
}
Functional Testing Concepts
-
Page Object Pattern
- A pattern that:
- reduces code duplication
- makes tests more readable and robust
- makes tests more maintanable
- They represent the services offered by a particular page i.e. models the 'page' for your test to interact with
- They should be the only thing that has a deep knowledge of the structure of the HTML of a page i.e. changes to interface / platform (e.g. web to native), should only affect page object: other parts of tests stay the same
Functional Testing Concepts with Cucumber (1/3)
Cucumber lets software development teams describe how software should behave in plain text
- Available on many platforms
- Utilizes Gherkin syntax
Functional Testing Concepts with Cucumber (2/3)
1: Feature: Some terse yet descriptive text of what is desired
2: Textual description of the business value of this feature
3: Business rules that govern the scope of the feature
4: Any additional info that will make the feature easier to understand
5:
6: Scenario: Some determinable business situation
7: Given some precondition
8: And some other precondition
9: When some action by the actor
10: And some other action
12: Then some testable outcome is achieved
13: And something else we can check happens too
14:
15: Scenario: A different situation
16: ...
Functional Testing Concepts with Cucumber (3/3)
Create .feature file (with many steps)
Write a single step definition
- Convert readable text to actual code / interactions
- With the correct plugins: Ctrl+Click step in .feature file to set up the function
Run tests and watch it fail
Implement code specified in step definition to make test pass
Run test to see step pass
Repeat 2-5 until all steps in .feature file implemented
Things to note
- Browser tests
- Beware the ajax loads and templates
- sleep() if you must, but it's not ideal: implicitlyWait() could be the answer
- Different environments respond differently on the same hardware
-
Code Coverage
-
Testing is not the end all and be all
In conclusion
- Testing is great
- Helps speed development
- Helps ensure that your code works
- Peace of mind while refactoring