XCUITest (iOS) Automation with POM Techniques
Can the POM technique be integrated with XCUITest for iOS? 🤔
Absolutely, yes. Apple introduced XCUITest automation for native iOS applications in 2015, providing testers with an additional tool for automation. If you’re familiar with the common automation combination of Appium and Selenium, then you’re likely already using the Page Object Model (POM) technique.
What is POM? 👀
In simple terms, POM is a design pattern that separates the UI elements from the tests, allowing for different operations on those elements. This technique treats UI elements and tests independently.
Let’s start creating a reliable, maintainable, and reusable XCUITest framework:
- Open your project in XCode and navigate to add a UI testing bundle template.
- Set the UI Testing Bundle Name and other settings.
- In the “Signing & Capabilities” tab, ensure that the “UI Testing” capability is enabled.
Once you’re ready, the project structure should look like this:
Example of a Page Object Class: MainScreen.swift
import Foundation
import XCTest
class MainScreen{
let app: XCUIApplication
let proceedButton: XCUIElement
let username: XCUIElement
let password: XCUIElement
init(app: XCUIApplication) {
self.app = app
proceedButton = app.buttons["Proceed"]
username = app.textFields["Username"]
password = app.textFields["Password"]
}
struct VerifyMessage {
struct MainScreen {
static let title = "Welcome to the Payment App"
}
func login(username: String, password: String) {
assertMainScreenTitle()
usernameField.typeText(username)
passwordField.typeText(password)
}
func tapProceedButton() {
proceedButton.tap()
}
func assertMainScreenTitle(){
XCTAssertEqual(app.staticTexts[VerifyMessage.MainScreen.title].label, "Welcome to the Payment App",
"Text mismatch in the label")
}
}
Example of a UI Test Class: UITestClass.swift
import XCTest
final class UITestClass: XCTestCase {
let app = XCUIApplication()
override class var runsForEachTargetApplicationUIConfiguration: Bool {
false
}
override func setUpWithError() throws {
continueAfterFailure = false
app.launchArguments = ["testing"]
app.launch()
}
override func tearDown() {
let screenshot = XCUIScreen.main.screenshot()
let attachment = XCTAttachment(screenshot: screenshot)
attachment.lifetime = .deleteOnSuccess
add(attachment)
app.terminate()
}
func testCancelButtonExists() throws {
let mainScreen = MainScreen(app:app)
mainScreen.login(username: "helloworld", password: "helloworld")
mainScreen.tapProceedButton()
}
To sum up, Page Object Model (POM) offers significant benefits for code structuring. By combining POM with best coding practices, you can create a robust and scalable iOS automation project. 🛠️