NSURLSession:后台上传,然后调用服务api

我正在尝试使用新的ios7背景传输api上传一些照片到服务器。 现在发生的事情是1)我们上传字节到s3 2)调用一个服务API来“完成”上传

我看了这个文档,似乎背景NSURLSession不支持“数据”任务。 这是否意味着我不能在实际上传完成后在后台执行第2步?

如果你想要一个简单的解决scheme,而不是为你的“完成”API调用重新调整NSURLSessionDownloadTask ,你可以在callback期间快速的http调用:

-URLSession:task:didCompleteWithError:

有背景任务的S3 在这里看到我的答案

另一个很好的资源是这里的苹果示例代码,并寻找“简单的后台传输”

您必须创build一个上传任务并从本地file upload。 在您的应用程序运行时,NSURLSessionTaskDelegate委托方法将在上传完成时专门完成:

  /* Sent as the last message related to a specific task. Error may be * nil, which implies that no error occurred and this task is complete. */ -(void)URLSession:(NSURLSession *)session task:(NSURLSessionTask *)task didCompleteWithError:(NSError *)error; 

如果你的应用程序去了背景,甚至被iOS(而不是用户)所杀,你的应用程序将被唤醒

 URLSessionDidFinishEventsForBackgroundURLSession 

然后你的NSURLsession委托方法将被调用

 - (void)URLSessionDidFinishEventsForBackgroundURLSession:(NSURLSession *)session 

你应该build立它的方式如下,在你的appDelegate添加

  - (void)application:(UIApplication *)application handleEventsForBackgroundURLSession:(NSString *)identifier completionHandler:(void (^)())completionHandler { /* Store the completion handler. The completion handler is invoked by the view controller's checkForAllDownloadsHavingCompleted method (if all the download tasks have been completed). */ self.backgroundSessionCompletionHandler = completionHandler; } 

然后在你的控制器/模型类中添加

  /* If an application has received an - application:handleEventsForBackgroundURLSession:completionHandler: message, the session delegate will receive this message to indicate that all messages previously enqueued for this session have been delivered. At this time it is safe to invoke the previously stored completion handler, or to begin any internal updates that will result in invoking the completion handler. */ - (void)URLSessionDidFinishEventsForBackgroundURLSession:(NSURLSession *)session { APLAppDelegate *appDelegate = (APLAppDelegate *)[[UIApplication sharedApplication] delegate]; if (appDelegate.backgroundSessionCompletionHandler) { void (^completionHandler)() = appDelegate.backgroundSessionCompletionHandler; appDelegate.backgroundSessionCompletionHandler = nil; completionHandler(); } NSLog(@"All tasks are finished"); } 

NSURLSessions具有委托方法URLSessionDidFinishEventsForBackgroundURLSession ,在会话完成其所有任务后URLSessionDidFinishEventsForBackgroundURLSession该方法。 我相信你应该在那里进行一个API呼叫。

 - (void)applicationDidEnterBackground:(UIApplication *)application { if([[UIDevice currentDevice] respondsToSelector:@selector(isMultitaskingSupported)]) { NSLog(@"Multitasking Supported"); __block UIBackgroundTaskIdentifier background_task; background_task = [application beginBackgroundTaskWithExpirationHandler:^ { //Clean up code. Tell the system that we are done. [application endBackgroundTask: background_task]; background_task = UIBackgroundTaskInvalid; }]; //To make the code block asynchronous dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0), ^{ //### background task starts NSLog(@"Running in the background\n"); while(TRUE) { NSLog(@"Background time Remaining: %f",[[UIApplication sharedApplication] backgroundTimeRemaining]); [NSThread sleepForTimeInterval:1]; //wait for 1 sec } //#### background task ends //Clean up code. Tell the system that we are done. [application endBackgroundTask: background_task]; background_task = UIBackgroundTaskInvalid; }); } else { NSLog(@"Multitasking Not Supported"); } } 

把这段代码放到appdelegate.m文件中

试试这个代码,希望它会有所帮助。