WWDC22 SALE: Save 50% on all my Swift books and bundles! >>

Ultimate Portfolio App - Error in UI Test - Cannot recognize the "NEW PROJECT" Edit Button

Forums > SwiftUI

My UI Test code:

func testEditingProjectUpdatesCorrectly() {
        app.buttons["Open"].tap()
        XCTAssertEqual(app.tables.cells.count, 0, "There should be no list rows initially.")

        app.buttons["Add Project"].tap()
        XCTAssertEqual(app.tables.cells.count, 1, "There should be 1 list row after adding a project.")

        app.buttons["NEW PROJECT"].tap()  **<<<---See Error details directly below this code **
        app.textFields["Project name"].tap()

        app.keys["space"].tap()
        app.keys["more"].tap() // more = 123 "key"
        app.keys["2"].tap()
        app.buttons["Return"].tap() // Return is a "button"...not a "key"

        app.buttons["Open Projects"].tap()
        XCTAssertTrue(app.buttons["New Project 2"].exists, "The new project name should be visible in the list.")
    }

ERROR: Failed to get matching snapshot: No matches found for Elements matching predicate '"NEW PROJECT" IN identifiers' from input {( Button, label: 'Home', Button, label: 'Open', Selected, Button, label: 'Closed', Button, label: 'Awards', Button, label: 'Sort', Button, label: 'Add Project', Button, label: 'Add New Item', Button, label: 'Compose' )}

I assume since the only button I cannot identify is [label: 'Compose'] that this must be the issue? This is likely the "Edit Project" button. I tried using "Compose" in place of "NEW PROJECT" but that did not work either. I tried it as both a button and a label.

My UI definitely has the words "NEW PROJECT" along with the "square.and.pencil" image to the right of the project name. Any ideas?

Thanks in advance!

Brad K.

1      

Or is this possibly a bug in Xcode Version 13.0 beta 4 (13A5201i) using Build Setting of iOS 14.7 running on Big Sur 11.4?

1      

hey @bradkimbrell, I'm having a similar issue to what you had by the sounds of it.

I was able to make the test work using "Compose" but then the updated project name isn't recognised.

Did you manage to find out where you were going wrong?

1      

I'm not sure when this UI test was broken and whether it is only due to iOS 15 or whether it is caused by the accessibility enhancements we have added to the project.

Basically we can say the button which is triggering the transition to EditProjectView is the NavigationLink containing Image(systemName: "square.and.pencil"). This SF Symbol has also the name "Compose". I suggest to replace it with the following Label:

Label("Edit Project", systemImage: "square.and.pencil")
    .labelStyle(.iconOnly)
    .imageScale(.large)

This ensures that VoiceOver knows that this button is about editing a project instead of "Compose" (whatever this would mean otherwise). Further it is using the translated names from the Localizable.strings file too.

To fix the UI test, you can then add a tap onto the EDIT PROJECT button. (It's in uppercase... don't know why yet, because the label is not visible on screen and therefore shouldn't be transformed)

See my changes in my version of the app.

EDIT: I've just tried to run the original UI test version (which did run 4 months ago) on an iOS 14.5 Simulator... and they were mostly broken: the buttons containing symbols/labels do not have proper label to identify them during the UI tests:

  ↪︎Find: Descendants matching type Button
    Output: {
      Button, {{2.0, 814.0}, {100.0, 48.0}}, label: 'Home'
      Button, {{106.0, 814.0}, {99.0, 48.0}}, label: 'Open', Selected
      Button, {{209.0, 814.0}, {100.0, 48.0}}, label: 'Closed'
      Button, {{313.0, 814.0}, {99.0, 48.0}}, label: 'Awards'
      Button, {{12.0, 44.0}, {47.7, 44.0}}, label: 'sort'
      Button, {{361.3, 44.0}, {40.7, 44.0}}, label: 'add'
    }

I've no idea how somebody runs regular UI tests with this broken system... Luckily it works again on iOS 15

EDIT 2: I've now analyzed more in detail why the UI tests broke on iOS 14.5 and I've fixed my UI tests in another change.

The problems were twofold:

  1. On iOS 14.5 (or before?) the accessibility attributes (label, identifier) of Button in the ToolbarItem cannot be set stay the same whatever you try... we only see the generated label of the SF Symbol (="add" and "sort" as shown above) which cannot be changed/influenced due to some bug (?).

  2. We use the modifier accessibilityElement(children: .combine) in ProjectHeaderView.swift to combine the project title Text view, the ProgressView and the edit button into a single element, making everything one button. This behaves differently on iOS 14 compared to iOS 15: the label and identifiers are combined which causes our headaches.

In my solution, I'm now using the accessibilityIdentifier for the relevant buttons ("Add Project", "Edit Project") and the project title text. Further I'm using NSPredicate based queries to find those elements because of the different way the accessibility identifiers are "combined" in iOS 14 and iOS 15.

In the end, my UI tests work again. :-)

1      

For Xcode 13.3.1 and a Simulator running iOS 15.4, I found this gets the test to work:

func testEditingProjectUpdatesCorrectly() {
    app.buttons["Open"].tap()
    XCTAssertEqual(app.tables.cells.count, 0, "There should be no list rows initially.")

    app.buttons["Add Project"].tap()
    XCTAssertEqual(app.tables.cells.count, 1, "There should be 1 list row after adding a project.")

    app.buttons["Compose"].tap()
    app.textFields["Project name"].tap()

    app.keys["space"].tap()
    app.keys["more"].tap()
    app.keys["2"].tap()
    app.buttons["Return"].tap()

    app.buttons["Open Projects"].tap()
    XCTAssertTrue(
        app.tables.progressIndicators["New Project 2"].exists,
        "The new project name should be visible in the list."
    )
}

A couple of things to note:

  • add is now Add Project
  • NEW PROJECT is now Compose
  • app.buttons["NEW PROJECT 2"].exists is now app.tables.progressIndicators["New Project 2"].exists

   

Hacking with Swift is sponsored by RevenueCat

SPONSORED In-app subscriptions are a pain. The code can be hard to write, hard to test, and full of edge cases. RevenueCat makes it straightforward and reliable so you can get back to building your app.

Explore the docs

Sponsor Hacking with Swift and reach the world's largest Swift community!

Reply to this topic…

You need to create an account or log in to reply.

All interactions here are governed by our code of conduct.

 
Unknown user

You are not logged in

Log in or create account
 

Link copied to your pasteboard.