【问题标题】:Xcode UI Test How to handle notification permissions generated by UNUserNotificationCenterXcode UI测试如何处理UNUserNotificationCenter生成的通知权限
【发布时间】:2018-09-04 07:31:21
【问题描述】:

在我的应用程序中,我要求这样的通知权限:

  UNUserNotificationCenter.current().requestAuthorization(options:[.badge, .alert, .sound]) { (granted, error) in

        if granted {
            DispatchQueue.main.async {
                UIApplication.shared.registerForRemoteNotifications()
            }
        }
    }

现在在测试时,我需要处理这个权限弹出但它不起作用,我尝试了这些代码:

XCUIApplication().alerts["“AppName” Would Like to Send You Notifications"].buttons["Allow"].tap() //didn't work.

addUIInterruptionMonitorWithDescription("Notification Dialog") { (alert) -> Bool in  
    alert.buttons["Allow"].tap()
    return true
}


addUIInterruptionMonitorWithDescription("“AppName” Would Like to Send You Notifications") { (alert) -> Bool in  
    alert.buttons["Allow"].tap()
    return true
}


addUIInterruptionMonitorWithDescription("Notifications may include alerts, sounds, and icon badges. These can be configured in Settings.") { (alert) -> Bool in  
    alert.buttons["Allow"].tap()
    return true
}

但是没有任何效果。

【问题讨论】:

    标签: swift xcode uitest


    【解决方案1】:

    试试这个

        let app2 = XCUIApplication(bundleIdentifier: "com.apple.springboard")
        let button = app2.alerts.firstMatch.buttons["Allow"]
        button.waitForExistence(timeout: 10)
        button.tap()
    

    【讨论】:

    • 非常有帮助。谢谢。出于某种原因,系统对话不再是应用程序的一部分? iOS 14.4、Xcode 12.4
    • UIInterruptionHandler 也可以。您必须在中断处理程序块之后添加 app.tap() 才能使其工作。但正如 Apple 建议的那样,它应该只用于您不知道它们何时会发生的警报。
    • 当我使用这种方法时,我在tap() 呼叫:[__NSArrayM insertObject:atIndex:]: object cannot be nil (NSInvalidArgumentException) 上收到此错误
    【解决方案2】:

    1/ 尝试使用 XCode 测试记录器记录路径以提醒按钮,并确保您拥有正确的按钮。

    XCUIApplication().alerts["“AppName” Would Like to Send You Notifications"].buttons["Allow"].tap() //didn't work.
    

    可能不正确。

    (注意:使用测试记录器来做一些事情,比如找到元素的路径是可以的,而且对新手非常友好。)

    2/ 您不必使用addUIInterruptionMonitorWithDescription 以防万一,您有一个每次都会发生的系统警报,或者您知道它会发生。 只需使用waitForExistance 并点击它(如果存在)。

    (注意:我发现等待和点击系统通知比addUIInterruptionMonitorWithDescription更好,这有时不稳定/复杂)

    3/ alert.buttons["Allow"].tap() 对我来说似乎不正确,不应该是 XCUIApplication().alerts.buttons["Allow"] 吗?或者,您可以使用XCUIApplication().alerts.buttons.element(boundBy: 0 点击第一个按钮。

    【讨论】:

      【解决方案3】:
      import XCTest
      
      // For multiple permission requests
      var isPhotoPermissionAvailable: Bool?
      var isLocationPermissionAvailable: Bool?
      var isNotificationsPermissionAvailable: Bool?
      
      extension XCTestCase {
      
          func allowPhotos(_ enabled: Bool = true) {
              addUIInterruptionMonitor(withDescription: "Photo Permissions") { (alert) -> Bool in
                  isPhotoPermissionAvailable = enabled
                  var alertButton = alert.buttons["Don't Allow"]
                  if enabled == true {
                      alertButton = alert.buttons["OK"]
                  }
                  if alertButton.exists {
                      alertButton.tap()
                      return true
                  }
                  XCUIApplication().tap()
                  return false
              }
              if isPhotoPermissionAvailable == nil {
                  XCUIApplication().swipeUp() //with this code, alert.buttons["OK"] exsists
              }
          }
      
          func allowLocation(_ enabled: Bool = true) {
              addUIInterruptionMonitor(withDescription: "Location Dialog") { (alert) -> Bool in
                  isLocationPermissionAvailable = enabled
                  var alertButton = alert.buttons["Don't Allow"]
                  if enabled == true {
                      alertButton = alert.buttons["Always Allow"]
                  }
                  if alertButton.exists {
                      alertButton.tap()
                      return true
                  }
                      XCUIApplication().tap()
                  return false
              }
              if isLocationPermissionAvailable == nil {
                  XCUIApplication().swipeUp()
              }
          }
      
          func allowNotifications(_ enabled: Bool = true) {
              addUIInterruptionMonitor(withDescription: "Notification Dialog") { (alert) -> Bool in
                  isNotificationsPermissionAvailable = enabled
                  var alertButton = alert.buttons["Don't Allow"]
                  if enabled == true {
                      alertButton = alert.buttons["Allow"]
                  }
                  if alertButton.exists {
                      alertButton.tap()
                      return true
                  }
                  XCUIApplication().tap()
                  return false
              }
              if isNotificationsPermissionAvailable == nil {
                  XCUIApplication().swipeUp()
              }
          }
      }
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2017-03-09
        • 2017-01-02
        • 1970-01-01
        • 2015-10-23
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多