performFetchWithCompletionHandler永远不会被解雇

1)我的plistconfiguration提供backgroundmode:

<key>UIBackgroundModes</key> <array> <string>fetch</string> </array> 

2)在didFinishLaunchingWithOptions我有:

 [[UIApplication sharedApplication] setMinimumBackgroundFetchInterval:1.0]; 

3)我在委托中声明了协议UIApplicationDelegate

4)我实现了下面的方法,但它永远不会被解雇。 (只有当我使用“XCode-> Debug-> Simulate Background Fetch”来模拟提取时才有效。)

 -(void)application:(UIApplication *)application performFetchWithCompletionHandler:(void (^)(UIBackgroundFetchResult))completionHandler 

为什么? 这是一个DP5testing版的错误? 我应该雷达吗?

恐怕这很难在设备上进行debugging,因为不能保证在指定的时间内调用它。

setMinimumBackgroundFetchInterval意味着它不会被调用的时间间隔小于您指定的值。 但是没有setMaximumBackgroundFetchInterval 。 因此,如果iOS决定每天只调用一次应用程序,或者每周只调用一次,则无论您的minimumBackgroundFetchInterval如何,都不会更频繁地调用您的应用程序。 AFAIK iOS决定什么时候调用performFetchWithCompletionHandler测量的模式,当用户启动应用程序的时间和频率。

在Xcode 5debugging模式下,您可以从菜单强制进行后台提取:debugging>模拟后台提取。

汪!

(只有当我使用“XCode-> Debug-> Simulate Background Fetch”来模拟提取时才有效。)

这是因为你在debugging模式。 请尝试启动没有XCode的应用程序。

使用你的设备,你可以使用以下步骤来启动application:performFetchWithCompletionHandler

  • 将您的应用程序置于“后台”状态
  • locking您的设备并等待5分钟。
  • 解锁你的设备,这将触发该方法

有很多考虑因素:

  1. 确保在plist中设置了后台获取function。

  2. 确保这个特定的应用程序,或一般来说,在设备的设置应用程序没有禁用后台提取function。

  3. 确保设置最小读取间隔。

  4. 确保你优雅地离开应用程序(例如,只要点击主页button,启动另一个应用程序和/或只是locking设备)。 但是,如果你杀了应用程序(双击主页button,向上滑动,或者你有什么),这将阻止操作系统提供你的应用程序一个机会来触发后续的后台提取请求(至less直到用户再次运行应用程序)。

  5. 确保你正在物理设备上进行testing,而不是通过Xcodedebugging器运行应用程序。 连接到debugging器会改变后台操作的行为。

  6. 确保应用程序实际上正在执行一些networking请求。 如果您的应用程序完全不执行networking请求,则不会参与后台获取。 例如,如果你做了一个带有“后台获取”的testing应用程序,并且不发出任何networking请求,你将不会参与后台获取。

    同样,如果操作系统在后台模式下启动您的应用程序,以便它可以执行后台获取,如果您没有实际执行networking请求,操作系统可能会停止提供您的应用程序在将来执行后台提取的能力。

  7. 确保调用完成处理程序,并在指定的时间内完成,否则将来您的应用程序可能不会参与后台提取。

  8. 操作系统执行后台获取的时间是由未被logging的规则决定的。 但相关因素包括:

    • 设备是否连接到电源和/或充足电;

    • 无论是否连接到WiFi;

    • 用户多久实际启动应用程序;

    • 设备是否正在执行其他networking相关任务(例如,后台提取是否可以与其他networking操作合并);

    • 过去后台提取请求的频率会导致数据可用。

    根据我的经验,第一次运行应用程序后,如果连接到wifi和电源,大约5分钟后唤醒设备,应用程序将执行后台获取。 这不是一条硬性规定,而是我们过去所经历的。

    但是许多新开发者在Stack Overflow上发布了一些问题,例如“我怎样才能让应用程序请求数据x分钟(或几小时)”,“如何每天凌晨2点要求数据”等等。简单的答案是,不能。 操作系统自行决定后台的时间。 你不能控制这个(除了最小请求间隔,但是你不能控制最大间隔,因为操作系统控制着这个间隔)。

  9. 这对许多人来说可能是显而易见的,但要确保你已经有了一个可靠的方法来了解后台获取过程是否正确运行。 用户通知框架可用于显示一些警报,以便知道后台请求是否导致了某些情况。 或者,可以使用os_log “统一通知”在macOS Console应用程序上监视的设备上发布消息。 但不止一次,我看到用户做了一些事情,比如等待消息在Xcode中显示或等待UIAlertController 。 你需要一些机制,当不连接到Xcode和应用程序永远不会进入前景。

另一件要检查的是你的plist文件。 确保UIApplicationExitsOnSuspend键不存在。

Stack Overflow上的许多人都build议使用该设置,以便在每次启动时强制应用程序重新启动。 这确实奏效,但副作用是它阻止了新的iOS 7后台抓取function被触发。

如果application: performFetchWithCompletionHandler:永远不会被解雇(除非你使用Xcode来模拟它),同样检查你的应用程序的“后台应用刷新”偏好是否为“开”。 (设置应用程序 – >常规 – >后台应用程序刷新)

另外,如果iPhone处于低功耗模式,背景获取将被禁用。

苹果公司提供了一个algorithm,根据你自己对应用的使用情况来定义后台提取应该触发的频率。 如果你使用它很多,那么它会尽可能频繁地获取,但是如果你每天下午四点使用,后台抓取应该在之前触发,所以当你启动它时你的数据会被更新。 参考这个链接