Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -11,17 +11,17 @@ class A11yOnboardingTests: BaseTestCase {
return "\(AccessibilityIdentifiers.Onboarding.onboarding)\(currentScreen)"
}

override func setUp() {
override func setUp() async throws {
launchArguments = [LaunchArguments.ClearProfile,
LaunchArguments.DisableAnimations,
LaunchArguments.SkipSplashScreenExperiment]
currentScreen = 0
super.setUp()
try await super.setUp()
}

override func tearDown() {
override func tearDown() async throws {
app.terminate()
super.tearDown()
try await super.tearDown()
}

func testA11yFirstRunTour() throws {
Expand Down
Original file line number Diff line number Diff line change
@@ -1,9 +1,6 @@
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/

import XCTest

@MainActor
class A11yUtils: XCTestCase {
Comment on lines 1 to 4
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Action required

1. a11yutils.swift missing mpl header 📘 Rule violation ✓ Correctness

• The Swift file no longer begins with the required Mozilla Public License v2.0 header comment
  block.
• This violates the licensing requirement for Swift source files and can create legal/compliance
  risk for redistributed source.
• The file currently starts directly with import XCTest, indicating the header is absent from the
  top of the file.
Agent prompt
## Issue description
`A11yUtils.swift` is missing the required Mozilla Public License v2.0 header at the top of the file.

## Issue Context
Compliance requires every `.swift` file to start with the exact MPL v2.0 header text.

## Fix Focus Areas
- firefox-ios/firefox-ios-tests/Tests/XCUITests/A11yUtils.swift[1-6]

ⓘ Copy this prompt and use it to remediate the issue with your preferred AI generation tools

public struct MissingAccessibilityElement {
public let elementType: String
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,8 @@ class ActivityStreamTest: FeatureFlaggedTestBase {
let testWithDB = ["testTopSites2Add", "testTopSitesRemoveAllExceptDefaultClearPrivateData"]
// Using the DDDBBs created for these tests containing enough entries for the tests that used them listed above
let pagesVisited = "browserActivityStreamPages-places.db"
override func setUp() {

override func setUp() async throws {
// Test name looks like: "[Class testFunc]", parse out the function name
let parts = name.replacingOccurrences(of: "]", with: "").split(separator: " ")
let key = String(parts[1])
Expand All @@ -41,16 +42,17 @@ class ActivityStreamTest: FeatureFlaggedTestBase {
}
launchArguments.append(LaunchArguments.SkipAddingGoogleTopSite)
launchArguments.append(LaunchArguments.SkipSponsoredShortcuts)
super.setUp()
try await super.setUp()
topSites = TopSitesScreen(app: app)
contextMenu = ContextMenuScreen(app: app)
tabTray = TabTrayScreen(app: app)
browser = BrowserScreen(app: app)
toolbar = ToolbarScreen(app: app)
}
override func tearDown() {

override func tearDown() async throws {
XCUIDevice.shared.orientation = .portrait
super.tearDown()
try await super.tearDown()
}

// https://mozilla.testrail.io/index.php?/cases/view/2273342
Expand Down
18 changes: 10 additions & 8 deletions firefox-ios/firefox-ios-tests/Tests/XCUITests/BaseTestCase.swift
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,9 @@ import Shared
let page1 = "http://localhost:\(serverPort)/test-fixture/find-in-page-test.html"
let page2 = "http://localhost:\(serverPort)/test-fixture/test-example.html"
let serverPort = ProcessInfo.processInfo.environment["WEBSERVER_PORT"] ?? "\(Int.random(in: 1025..<65000))"
@MainActor
let urlBarAddress = XCUIApplication().textFields[AccessibilityIdentifiers.Browser.AddressToolbar.searchTextField]
@MainActor
let homepageSearchBar = XCUIApplication().cells[AccessibilityIdentifiers.FirefoxHomepage.SearchBar.itemCell]

func path(forTestPage page: String) -> String {
Expand Down Expand Up @@ -107,16 +109,16 @@ class BaseTestCase: XCTestCase {
}
}

override func setUp() {
super.setUp()
override func setUp() async throws {
try await super.setUp()
continueAfterFailure = false
setUpApp()
setUpScreenGraph()
}

override func tearDown() {
override func tearDown() async throws {
app.terminate()
super.tearDown()
try await super.tearDown()
}
Comment on lines +112 to 122
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Action required

5. Restart helper now wrong 🐞 Bug ⛯ Reliability

BaseTestCase.setUp/tearDown were migrated to async throws, but forceRestartApp() still calls
  synchronous tearDown()/setUp().
• This likely calls XCTest’s synchronous lifecycle methods (not BaseTestCase’s async ones), so the
  app may not actually restart and the screen graph may not be rebuilt.
• Tests relying on forceRestartApp() to validate persistence across restart become
  incorrect/flaky.
Agent prompt
### Issue description
`forceRestartApp()` is synchronous but `BaseTestCase` lifecycle is now `async throws`. The helper can no longer reliably restart the app / rebuild state.

### Issue Context
Tests use `forceRestartApp()` to verify persistence across restart.

### Fix Focus Areas
- firefox-ios/firefox-ios-tests/Tests/XCUITests/BaseTestCase.swift[112-122]
- firefox-ios/firefox-ios-tests/Tests/XCUITests/BaseTestCase.swift[139-142]

ⓘ Copy this prompt and use it to remediate the issue with your preferred AI generation tools

Comment on lines +119 to 122
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Action required

6. Sync teardown skipped 🐞 Bug ⛯ Reliability

• Several BaseTestCase-derived test classes still override *synchronous* tearDown() and call
  super.tearDown() (sync).
• With BaseTestCase now implementing tearDown() async throws, XCTest will use the async tear
  down path, so these synchronous overrides’ cleanup (orientation/theme reset, downloads cleanup) can
  be skipped.
• This risks cross-test pollution and UI-test flakiness (e.g., device left in landscape).
Agent prompt
### Issue description
Some test classes still override synchronous `tearDown()`, which is now disconnected from the async teardown path.

### Issue Context
`BaseTestCase` teardown is now `async throws`. Subclasses should override the same signature to ensure cleanup runs.

### Fix Focus Areas
- firefox-ios/firefox-ios-tests/Tests/XCUITests/BaseTestCase.swift[119-122]
- firefox-ios/firefox-ios-tests/Tests/XCUITests/ToolbarMenuTests.swift[8-12]
- firefox-ios/firefox-ios-tests/Tests/XCUITests/SettingsTests.swift[10-19]
- firefox-ios/firefox-ios-tests/Tests/XCUITests/DownloadsTests.swift[18-41]
- firefox-ios/firefox-ios-tests/Tests/XCUITests/DragAndDropTests.swift[28-31]
- firefox-ios/firefox-ios-tests/Tests/XCUITests/SwipingTabsTests.swift[9-12]
- firefox-ios/firefox-ios-tests/Tests/XCUITests/HomeButtonTests.swift[8-11]

ⓘ Copy this prompt and use it to remediate the issue with your preferred AI generation tools


var skipPlatform: Bool {
Expand Down Expand Up @@ -503,19 +505,19 @@ class BaseTestCase: XCTestCase {
}

class IpadOnlyTestCase: BaseTestCase {
override func setUp() {
override func setUp() async throws {
specificForPlatform = .pad
if iPad() {
super.setUp()
await super.setUp()
}
Comment on lines +508 to 512
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Action required

4. Missing try await 🐞 Bug ✓ Correctness

IpadOnlyTestCase.setUp() calls await super.setUp() even though the superclass setUp() is
  async throws.
• This is a compile-time error that will block building the UI test target.
Agent prompt
### Issue description
`IpadOnlyTestCase.setUp()` calls a throwing async method without `try`, which is a compile error.

### Issue Context
`BaseTestCase.setUp()` is `async throws`, so platform-specific subclasses must call it with `try await`.

### Fix Focus Areas
- firefox-ios/firefox-ios-tests/Tests/XCUITests/BaseTestCase.swift[507-523]

ⓘ Copy this prompt and use it to remediate the issue with your preferred AI generation tools

}
}

class IphoneOnlyTestCase: BaseTestCase {
override func setUp() {
override func setUp() async throws {
specificForPlatform = .phone
if !iPad() {
super.setUp()
try await super.setUp()
}
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,8 +18,8 @@ class BookmarksTests: FeatureFlaggedTestBase {
private var homepageSettingsScreen: HomepageSettingsScreen!
private var firefoxHomeScreen: FirefoxHomePageScreen!

override func setUp() {
super.setUp()
override func setUp() async throws {
try await super.setUp()
topSitesScreen = TopSitesScreen(app: app)
browserScreen = BrowserScreen(app: app)
toolbarScreen = ToolbarScreen(app: app)
Expand All @@ -28,9 +28,9 @@ class BookmarksTests: FeatureFlaggedTestBase {
firefoxHomeScreen = FirefoxHomePageScreen(app: app)
}

override func tearDown() {
override func tearDown() async throws {
XCUIDevice.shared.orientation = .portrait
super.tearDown()
try await super.tearDown()
}

private func checkBookmarked() {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,9 +21,9 @@ class BrowsingPDFTests: BaseTestCase {
private var contextMenu: ContextMenuScreen!
private var library: LibraryScreen!

override func setUp() {
override func setUp() async throws {
// Test name looks like: "[Class testFunc]", parse out the function name
super.setUp()
try await super.setUp()
topSites = TopSitesScreen(app: app)
contextMenu = ContextMenuScreen(app: app)
pdf = PDFScreen(app: app)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,8 +13,9 @@ class O_AddressesTests: BaseTestCase {
private var settingsScreen: SettingScreen!
private var browserScreen: BrowserScreen!

override func setUp() {
super.setUp()
override func setUp() async throws {
try await super.setUp()

if #available(iOS 16, *) {
if !name.contains("testAddressOptionIsAvailableInSettingsMenu") {
navigator.nowAt(NewTabScreen)
Expand All @@ -34,13 +35,13 @@ class O_AddressesTests: BaseTestCase {
browserScreen = BrowserScreen(app: app)
}

override func tearDown() {
override func tearDown() async throws {
if name.contains("testAddressOptionIsAvailableInSettingsMenu") {
switchThemeToDarkOrLight(theme: "Light")
XCUIDevice.shared.orientation = .portrait
}
app.terminate()
super.tearDown()
try await super.tearDown()
}

// https://mozilla.testrail.io/index.php?/cases/view/2618637
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,15 +8,15 @@ final class CookiePersistenceTests: BaseTestCase {
let cookieSiteURL = "http://localhost:\(serverPort)/test-fixture/test-cookie-store.html"
let topSitesTitle = ["Facebook", "YouTube", "Wikipedia"]

override func setUp() {
override func setUp() async throws {
// Fresh install the app
// removeApp() does not work on iOS 15 and 16 intermittently
if #available(iOS 17, *) {
removeApp()
}

// The app is correctly installed
super.setUp()
try await super.setUp()
}

func testCookiePersistenceBasic() {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ class DatabaseFixtureTest: BaseTestCase {
"testHistoryDatabaseFixture": "testHistoryDatabase100-places.db"
]

override func setUp() {
override func setUp() async throws {
// Test name looks like: "[Class testFunc]", parse out the function name
let parts = name.replacingOccurrences(of: "]", with: "").split(separator: " ")
let key = String(parts[1])
Expand All @@ -21,7 +21,7 @@ class DatabaseFixtureTest: BaseTestCase {
LaunchArguments.LoadDatabasePrefix + fixtures[key]!,
LaunchArguments.SkipContextualHints,
LaunchArguments.DisableAnimations]
super.setUp()
try await super.setUp()
}

// https://mozilla.testrail.io/index.php?/cases/view/2458579
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -93,10 +93,10 @@ class DesktopModeTestsIphone: BaseTestCase {
var toolbarScreen: ToolbarScreen!
var mainMenuScreen: MainMenuScreen!

override func setUp() {
override func setUp() async throws {
specificForPlatform = .phone
if !iPad() {
super.setUp()
try await super.setUp()
}
browserScreen = BrowserScreen(app: app)
toolbarScreen = ToolbarScreen(app: app)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
import XCTest

class DisplaySettingTests: BaseTestCase {
override func setUp() {
override func setUp() async throws {
// Fresh install the app
// removeApp() does not work on iOS 15 and 16 intermittently
if name.contains("testCheckDisplaySettingsDefault") {
Expand All @@ -14,7 +14,7 @@ class DisplaySettingTests: BaseTestCase {
}
}
// The app is correctly installed
super.setUp()
try await super.setUp()
}

// https://mozilla.testrail.io/index.php?/cases/view/2337485
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ class DomainAutocompleteTests: BaseTestCase {
// This DB contains 3 entries mozilla.com/github.com/git.es
let historyDB = "browserAutocomplete-places.db"

override func setUp() {
override func setUp() async throws {
// Test name looks like: "[Class testFunc]", parse out the function name
let parts = name.replacingOccurrences(of: "]", with: "").split(separator: " ")
let key = String(parts[1])
Expand All @@ -41,7 +41,7 @@ class DomainAutocompleteTests: BaseTestCase {
LaunchArguments.SkipContextualHints,
LaunchArguments.DisableAnimations]
}
super.setUp()
try await super.setUp()
}

// https://mozilla.testrail.io/index.php?/cases/view/2334558
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -291,7 +291,7 @@ class DragAndDropTestIpad: IpadOnlyTestCase {
// This DDBB contains those 4 websites listed in the name
let historyAndBookmarksDB = "browserYoutubeTwitterMozillaExample-places.db"

override func setUp() {
override func setUp() async throws {
// Test name looks like: "[Class testFunc]", parse out the function name
let parts = name.replacingOccurrences(of: "]", with: "").split(separator: " ")
let key = String(parts[1])
Expand All @@ -304,12 +304,12 @@ class DragAndDropTestIpad: IpadOnlyTestCase {
LaunchArguments.SkipContextualHints,
LaunchArguments.DisableAnimations]
}
super.setUp()
try await super.setUp()
}

override func tearDown() {
override func tearDown() async throws {
XCUIDevice.shared.orientation = UIDeviceOrientation.portrait
super.tearDown()
try await super.tearDown()
}

// https://mozilla.testrail.io/index.php?/cases/view/2307024
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,14 +5,14 @@
import XCTest

class EngagementNotificationTests: BaseTestCase {
override func setUp() {
override func setUp() async throws {
// Fresh install the app
// removeApp() does not work on iOS 15 and 16 intermittently
if #available(iOS 17, *) {
removeApp()
}
// The app is correctly installed
super.setUp()
try await super.setUp()
}

// https://mozilla.testrail.io/index.php?/cases/view/2307101
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -43,10 +43,10 @@ class FeatureFlaggedTestSuite: FeatureFlaggedTestBase {
addLaunchArgument(jsonFileName: jsonFileName, featureName: featureName)
}

override func setUp() {
override func setUp() async throws {
continueAfterFailure = false
setUpExperimentVariables()
setUpApp()
setUpExperimentVariables()
setUpLaunchArguments()
setUpScreenGraph()
}
Comment on lines +46 to 52
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Action required

7. Feature suite order crash 🐞 Bug ✓ Correctness

FeatureFlaggedTestSuite.setUp() now calls setUpApp() before setUpExperimentVariables().
• But setUpApp() immediately uses jsonFileName/featureName, which are String! and documented
  to be set inside setUpExperimentVariables().
• If this base class is used, it can crash with an unexpected nil unwrap during setup.
Agent prompt
### Issue description
`FeatureFlaggedTestSuite.setUp()` uses IUO properties before they are initialized.

### Issue Context
`jsonFileName` / `featureName` are expected to be set by `setUpExperimentVariables()`.

### Fix Focus Areas
- firefox-ios/firefox-ios-tests/Tests/XCUITests/FeatureFlaggedTestBase.swift[37-52]

ⓘ Copy this prompt and use it to remediate the issue with your preferred AI generation tools

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ import Foundation
import MappaMundi
import XCTest

@MainActor
func createScreenGraph(for test: XCTestCase, with app: XCUIApplication) -> MMScreenGraph<FxUserState> {
let map = MMScreenGraph(for: test, with: FxUserState.self)

Expand Down Expand Up @@ -123,31 +124,38 @@ let allHomePanels = [
LibraryPanel_Downloads
]

@MainActor
let iOS_Settings = XCUIApplication(bundleIdentifier: "com.apple.Preferences")
@MainActor
let springboard = XCUIApplication(bundleIdentifier: "com.apple.springboard")

@MainActor
func navigationControllerBackAction(for app: XCUIApplication) -> () -> Void {
return {
app.navigationBars.element(boundBy: 0).buttons.element(boundBy: 0).waitAndTap()
}
}

@MainActor
func cancelBackAction(for app: XCUIApplication) -> () -> Void {
return {
app.otherElements["PopoverDismissRegion"].waitAndTap()
}
}

@MainActor
func dismissContextMenuAction(app: XCUIApplication) -> () -> Void {
return {
app.coordinate(withNormalizedOffset: CGVector(dx: 0.5, dy: 0.25)).tap()
}
}

@MainActor
func select(rows: Int, in app: XCUIApplication) {
app.staticTexts[String(rows)].firstMatch.waitAndTap()
}

@MainActor
func type(text: String, in app: XCUIApplication) {
text.forEach { char in
app.keys[String(char)].waitAndTap()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,7 @@ class HistoryTests: BaseTestCase {
var browserScreen: BrowserScreen!
var historyScreen: HistoryScreen!

override func setUp() {
override func setUp() async throws {
// Test name looks like: "[Class testFunc]", parse out the function name
let parts = name.replacingOccurrences(of: "]", with: "").split(separator: " ")
let key = String(parts[1])
Expand All @@ -57,7 +57,7 @@ class HistoryTests: BaseTestCase {
LaunchArguments.SkipContextualHints,
LaunchArguments.DisableAnimations]
}
super.setUp()
try await super.setUp()
toolbarScreen = ToolbarScreen(app: app)
settingScreen = SettingScreen(app: app)
browserScreen = BrowserScreen(app: app)
Expand Down
Loading