“Unexpected swift error… extra argument in call when compiling a test target or running tests”

This threw me. The underlying problem is straightforward but the error is misleading, for interesting reasons.

This was in a simple test case:

import Foundation
 import XCTest
 import SONR

class UserTests : DataTests {
 func testCreate() {
 let json : JSON = “{}”
 let user = User(json:json)
 }
 }

If I do a full build I am getting the same error as in the IDE…

/Code/SONR/SONRTests/UserTests.swift:16:24: error: extra argument ‘json’ in call

let user = User(json:json)

^ ~~~~

Why are we getting this? If I remove the json:json and just use User() it’s fine. If I right click on the user class it goes to the User.swift file in my main project and I can clearly see my convenience initialiser there, which it should be picking up…

convenience init(json : JSON) {
 self.init()
 Id = json[“Id”].int64Value
 UserName = json[“UserName”].stringValue
 ScreenName = json[“ScreenName”].stringValue
 Email = json[“Email”].string
 PhoneNumber = json[“PhoneNumber”].string
 }

This looks fine and other code in my main project is using it fine. I copied and pasted my test code from working code elsewhere in the project.

I had a suspicion so I checked if the User.swift file was being linked into the SONRTests target. It wasn’t. Aha! But why is the class recognized at all? Because I’m importing the SONR module, the main project. But here’s the key fact. While most initialisers in User are public, the json initialiser doesn’t have the keyword public. So from outside the SONR module it’s not visible and the tests are being compiled into a separate module SONRTests. From the point of view of that module, the exposed interface of User is…

public class User : NSObject,NSCoding {
 required public override init()
 required public init(coder aDecoder: NSCoder)
 public func encodeWithCoder(aCoder: NSCoder)
 public func description() -> String
 public func addEvent(event : Event)
 }

So you can see we need to be careful with what’s public, given the fact that the test cases are in a separate module. Another alternative, which I’m probably going with, is to link the User class into the SONRTests module as well so that the tests have access to non public (internal) functions.

Like this:

Like Loading…

Related


Originally published at petosoft.wordpress.com on February 18, 2015.

One clap, two clap, three clap, forty?

By clapping more or less, you can signal to us which stories really stand out.