Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Understanding XCTest framework

Swift India
November 16, 2019

Understanding XCTest framework

Swift India

November 16, 2019
Tweet

More Decks by Swift India

Other Decks in Technology

Transcript

  1. Agenda • Understanding how XCTests work • Life cycle of

    an object in XCTest • Efficient use of setUp and tearDown • Using tearDown blocks • Testing memory leaks using XCTests

  2. XCTestCase subclasses Test methods e.g func testValue() { // testing

    logic } testMethod1() —XCTestCaseObj1 testMethod2() —XCTestCaseObj2 ———————————————— - no arguments, 
 - no return types, 
 - begins with word “test” Collection How XCTest Works
  3. class XCTestDemoIntegerTests: XCTestCase { var counter: Int = 1 func

    testIncrement() { counter += 1 XCTAssertEqual(counter, 2) } func testDecrement() { counter -= 1 XCTAssertEqual(counter, 1) } } class XCTestDemoIntegerTests: XCTestCase { var counter: Int = 1 func testIncrement() { counter += 1 XCTAssertEqual(counter, 2) } func testDecrement() { counter -= 1 } } Example XCTAssertEqual(counter, 0)
  4. XCTest - Object life cycle • has to be released

    explicitly
 
 • create in setUp - cleanup in tearDown
 
 • might affect result of other tests if not released
  5. class XCTestObjectLifeCycleTest: XCTestCase { private var storageManager: DataStorageManager! override func

    setUp() { super.setUp() storageManager = DataStorageManager() storageManager.store(data: (["someKey": "someData"])) } func testDataStoreManager() { XCTAssertEqual(storageManager.fetchStoredData().count, 1) } } Example
  6. class DataStorageManager { init() { prepare() } private func prepare()

    { // setup DB connection // write to UserDefaults } /// Stores the given data in file system/DB or some other storage method func store(data: Any) { } func fetchData() -> [Any] { return ["some data"] } func clean() { // close db connection // remove files // clear UserDefaults } deinit { clean() } }
  7. class XCTestObjectLifeCycleTest: XCTestCase { private var storageManager: DataStorageManager! override func

    setUp() { super.setUp() storageManager = DataStorageManager() storageManager.store(data: (["someKey": "someData"])) } func testDataStoreManager() { XCTAssertEqual(storageManager.fetchStoredData().count, 1) } override func tearDown() { super.tearDown() } } storageManager = nil Example
  8. setUp() class method scope - global to all tests setup

    initial state for all tests setUp() instance method scope - local to each test setup initial state before each test begins tearDown() class method scope - global to all tests final clean up for all tests tearDown() instance method scope - global to all tests clean up before each test ends setUp and tearDown
  9. tearDown blocks • Registers a block to be invoked when

    test method ends • Always invoked before tearDown() instance method • Can add multiple tearDown blocks, executed in LIFO order • Invoked on the main thread
  10. class XCTestTearDownBlockTest: XCTestCase { func testStorageManager() { let manager =

    storageManagerForData(["someKey": "someData"]) let storedData = manager.fetchStoredData() XCTAssertTrue(storedData.count == 1) } private func storageManagerForData(_ data: Any) -> DataStorageManager { let storageManager = DataStorageManager() storageManager.store(data: data) return storageManager } } Example addTeardownBlock { storageManager.clean() }
  11. setUp() class method setUp() instance method tearDownBlock n tearDownBlock 1

    tearDown() instance method tearDown() class method tearDownBlock n-1 Order of Execution testMethod1() repeats for each test method 1. 2. 3. 4. 5. 6.
  12. Testing memory leaks • We can write test cases to

    check memory leaks by keeping a weak reference to the object in our test class • Check that the weak reference in nil the tearDown() method • Demo • Source: https://www.essentialdeveloper.com