How to use XCTAssertThrowsSpecific

ios, nsexception, objective-c, unit-testing, xctest

Solution

You should only use exceptions for exceptional cases, not for error handling and flow control

Having said that, here's how you use `XCTAssertThrowsSpecific`:

`XCTAssertThrowsSpecific` expects the specific class of the exception as the second parameter. `NSCAssert` throws an `NSException`. To test for that, use

XCTAssertThrowsSpecific([object methodThatShouldThrow], NSException, @"should throw an exception");

Now, that won't help much, because it's likely that every exception is an `NSException` or a subclass thereof.

`NSException`s have a `name` property that determines the type of the exception. In case of `NSCAssert` this is `NSInternalInconsistencyException`. To test for that, use `XCTAssertThrowsSpecificNamed`

XCTAssertThrowsSpecificNamed(
  [object methodThatShouldThrow],
  NSException,
  NSInternalInconsistencyException,
  @"should throw NSInternalInconsistencyException"
);

Problem

I'm writing Cocoa unit tests using XCTest and recently used XCTAssertThrows for the first time. That's pretty cool, but I want to make it even better with XCTAssertThrowsSpecific and requiring a certain exception. Here is an example test: ``` -(void)testShortPassword { XCTAssertThrows([user storePassword:@"abc"],@"Expect exception for short pw"); } ``` And on my user class I have the following code: ``` -(void)storePassword:(NSString*)password { NSCAssert(password.length > 6, @"Password must be longer than 6 characters"); // go on to store the password on the keychain } ``` Keeping in mind that Cocoa in general shies away from using exceptions (so it might be better to return an error, and show UI in the preceding example, etc.) How do I throw an exception in a manner that can be caught by `XCTAssertThrowsSpecific`? How do I specify that in `XCTAssertThrowsSpecific(expression, specificException, format...)`?

Original source