'XCTAssertEqual gives me error - UIViewController.Type cannot conform to 'Equatable'

I have an enum like following-

enum Vehicle: String, CaseIterable {
        case car = "/car/"
        case boat = "/plane"
        case bicycle = "/bicycle/"
        case train = "/train"
        
        var targetControllerType: UIViewController.Type? {
            switch self {
            case .car:
                return FourWheelerViewController.self
            case .boat:
                return NoWheelerViewController.self
            case .bicycle:
                return TwoWheelerViewController.self
            case .train:
                return MultiWheelerViewController.self
            }
        }
}

when I do equality check, it works -

if Vehicle.train.targetControllerType == MultiWheelerViewController.self {
     print("It's true")
}

but when I try to write test case for it like -

func testTrainTargetViewControllerType() {
        XCTAssertEqual(Vehicle.train.targetControllerType, MultiWheelerViewController.self)
}

I get compile time error -

Type UIVewController.Type" canot conform to 'Equatable'.

Can anyone tell me what's going on here and why.



Solution 1:[1]

As the error says, Type can't conform to Equatable. But you can still test for equality using ==:

func testTrainTargetViewControllerType() {
    XCTAssertTrue(Vehicle.train.targetControllerType == MultiWheelerViewController.self)
}

This passes. But if the test should fail, it doesn't say why. We normally get a helpful message from XCTAssertEqual because it can say the left side doesn't equal the right side, so we can see both values.

But every XCTest assertion has an optional message, where we can add information. So add a message stating what you expected, and what the actual result was:

func testTrainTargetViewControllerType() {
    XCTAssertTrue(
        Vehicle.train.targetControllerType == MultiWheelerViewController.self,
        "Expected MultiWheelerViewController, but was \(String(describing: Vehicle.train.targetControllerType))"
    )
}

Force a test to fail to see how useful it is. If I break the code on purpose, I see:

XCTAssertTrue failed - Expected MultiWheelerViewController, but was Optional(MyProject.TwoWheelerViewController)

This way, if anything goes wrong, you have the information you need to understand why it failed the assertion.

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1 Jon Reid