XCTAssert break function
Asked Answered
F

1

13

How to stop unit test execution if a logic is failed. Below is the example. How to stop execution when XCTAssertEqual("Hello", "Hi", "Passed") condition is failed.

func test_one() 
{    
    XCTAssertEqual("Hello", "Hi", "Passed")    
    let b = "Good Morning!" 
    // code continues...
}
Federalize answered 5/8, 2015 at 19:36 Comment(7)
You should only have one assert per test, and it should be the last line in your test, so this really is a problem with your code structure, which again means a good answer can't really be provided for your problem.Aragonite
I will be difficult if we are testing a parsing logic. What I mean is I have a service response, I have to parse the data and store it in database. I have to test if the parsing of the response is proper. Obviously i will have entire parsing logic in a single function, and so there will be multiple assert conditions.. please correct me if i am wrongFederalize
No, you can just do a common setup, and have individual asserts in each test. Multiple asserts means you don't know why the test failed without reading the logs in details, which is breaks the idea of fast feedbackAragonite
While I certainly agree that tests should not test too much, that does not mean there should only be 1 assert per test. Ex. Testing the "add" method of an array. You might want to check that add returns true for successfully adding and that the count increased by one. Ex 2. If a block returns that has an error and a response, you will want to assert that the error is nil and the response is "x" valueAcid
You can still write that as two tests. And if you written your tests good, it's just 1 extra line aside from the function declaration in the first place. I'll recommend reading osherove.com/blog/2005/4/14/…Aragonite
I think the idea of one assert per test seems very unrealistic. You would end up with 1000s of tests with tens of thousands of lines of identical code - or a complex subclassing structure. With continueAfterFailure set to false the test stops anyway after one asset fails and with a message on each assert so you can go directly to the one that is failing. Once the test is passing, it can be ignored - unless regression causes it to fail again. The overhead of duplicating and managing such a huge additional codebase would be a significant drag. So what is the benefit of this rule?Hereafter
@ClausJørgensen, the link you pointed to does not apply to Swift, since all of the asserts in a test method are executed, you don't get only the first 'symptom' (as the blog post names them). Furthermore, related asserts are going to fail together in a single method so it's easier to make the connection. (Having said that, what the OP asks and the answer provided defeat that mechanism, I agree on that. But sometimes, you just want to fail fast)Desirae
A
37

XCTestCase has a variable var continueAfterFailure: Bool which defaults to true. This means that the test continues running even after a test fails

override func setUp() {
    super.setUp()
    // Put setup code here. This method is called before the invocation of each test method in the class.
    continueAfterFailure = false
}
Acid answered 5/8, 2015 at 19:44 Comment(3)
Thanks Kevin. Can I use this continueAfterFailure in between 2 assert conditions. As mentioned in my question, if the XCTAssert 1 condition is failed, XCTAssert 2 condition should not be executed.Federalize
That is what will happen when you set continuedAfterFailure to falseAcid
Awesome! did not know about this!Determiner

© 2022 - 2024 — McMap. All rights reserved.