Blog Layout

Undefined symbol in Swift test cases

Raphael Haase • April 7, 2022

I recently created a new iOS project in Xcode 13.3 and stumbled into a really annoying error which is not yet documented, but easy to fix.



What went wrong?

So let's look into how we can reproduce this error for a moment:


1. Create a new iOS Multiplatform project in XCode.


2. Give it any suitable name and include test cases from the creation wizard.


3. Create a new Swift file and call it MagicModel.swift.


4. Add some simple stub code like:


struct MagicModel {

  var title: String

}


5. Do not add MagicModel.swift to the test target, we are going to use   @testable import instead.


5. Go to the automatically created test case file Tests_iOS.swift.


6. Add a trivial test case like:


func testMagicModel() throws {

    let magicModel = MagicModel(title: "The model")

}


and add @testable import YourAppName after the import XCTest on the top of the file.


Undefined Symbol error


Next up, when you try to run the tests you will get a compiler error message:


Undefined symbol: YourAppName.MagicModel.init(title: Swift.String) -> YourAppName.MagicModel



Don't panic


Luckily, you don't need to panic, because the cause of this issue and the solution are really simple:


The default unit test type in that file producing the compiler error is a UI test instead of a normal unit test.

UI tests do not support @testable import.


Use or create a Unit Test target, not a UI Test target


So the solution is to add that test you were working on to a Unit Test target instead of the default UI Test target.


In case you do not have a Unit Test target yet, create one by:


  1. Clicking on the project in the project navigator.
  2. Under General and Targets, click on the + icon on the bottom.
  3. Search for Unit Test and select Unit Testing Bundle.


Check out the code on github


If you are lazy, clone my project from github:


https://github.com/rph8/UndefinedSymbolApp


It shows the solution, i.e. how it works.


If you uncomment the lines in Tests_iOS, you can see how it does not work.

This is where you would typically go wrong.

A robotic hand automates testing on Apple devices by touching them
By Raphael Haase February 9, 2023
Automated testing is a must for any app on iOS. It not only saves time, it is crucial for ensuring consistently good user experience and data security of your apps.
By Raphael Haase December 15, 2022
Automatisiertes Testen ist eine Technik, bei der vorher festgelegte Tests für eine mobile Anwendung automatisch ausgeführt werden. Dies kann dazu beitragen, die Qualität und Zuverlässigkeit einer App sicherzustellen, indem Fehler und andere Probleme erkannt werden, bevor die App veröffentlicht wird. Gerade auch, wenn es nur um ein Update gibt. Denn so genannte Regressionen, Fehler die wieder zurück kommen, können einer App ordentlich Probleme bereiten. Einige Vorteile von automatisierten Tests für iOS und Android sind:
Automatisiertes Testen auf iPhones durch Roboterhände
By Raphael Haase December 1, 2022
In der Medizin- und Finanzbranche ist die Entwicklung von iOS-Apps, die zuverlässig und genau sind, unerlässlich. Automatisierte Tests können dabei helfen, diesen Prozess einfacher und effizienter zu gestalten. Werfen wir also einen Blick auf die Vorteile des automatisierten Testens bei der Entwicklung von iOS-Apps in der Medizin- oder Finanzbranche.
By Raphael Haase October 20, 2022
Entwickelt man heute mobile Anwendungen für iOS oder Android, dann heisst es häufig man müsse unbedingt einem bestimmten Architektur-Pattern folgen wie MVVM oder VIPER. Sonst würde sofort die App schlecht werden. Nun ist es nicht verkehrt gewissen Mustern zu folgen, denn das macht es für andere Entwickler einfach den Code zu verstehen und man hilft natürlich auch sich selbst dabei, das Rad nicht neu zu erfinden. Das Problem ist aber, dass nicht alle Architektur-Muster gleichermassen geeignet sind. Am wichtigsten ist dabei wohl, dass viele Architektur-Muster für kleine Anwendungen mit 1-2 Entwicklern irgendetwas zwischen Overkill oder sogar Kontraproduktivität sind. 
Standup Paddling ist manchmal besser als ein Daily Standup
By Raphael Haase October 6, 2022
Viele tun es, nicht alle lieben es: Das "Daily Standup". Heute geht es darum, warum ich dieses Ritual kritisch sehe und zu einem Umdenken rate.
A software developer leaving the team
By Raphael Haase September 22, 2022
It's every CTO's worst nightmare: your developers are the lifeblood of your company. They manage our most valuable digital assets and without them, you can't launch or maintain any meaningful customer engagement plans. But what happens when one of these key members suddenly walks away from their post with little to no notice? Suddenly, you've got a critical hole in your product development team that needs to be filled – but fast! You must find a replacement quickly. But even then, there’s still the daunting task of ensuring continuity in launching and maintaining new products as well as existing applications already live on the market. In this blog post, we'll discuss ways to make sure your app stays up and running even if (or especially if!) a developer decides to move on swiftly leaving behind incomplete projects for whoever steps up next.
Monterey landscape
By Raphael Haase February 17, 2022
A quick recipe on how you can add a new path or folder to "the" command line path.
A different kind of brew
By Raphael Haase February 3, 2022
If you do not want homebrew services to start again at each launch, follow these steps.
Pipelines
By Raphael Haase January 20, 2022
Add multiline bash scripts in Azure Pipelines like this.
By Raphael Haase January 6, 2022
How to setup the Jazzy documentation tool for Swift on an M1 / Apple Silicon Mac.
More Posts
Share by: