我的前面两篇文章介绍了NSURLSession套件的使用和NSURLSession套件的主要类。今天我们使用NSURLSession来完成一个小的应用程序。在实战之前,我先补充一点,为什么苹果会主推NSURLSession技术,而放弃大家都熟悉的NSURLConnection技术,苹果这么做肯定是有原因的,下面列举了NSURLSession的优点:

1.后台上传和下载。当你的程序退出了也能进行网络操作,这对用户和APP来说都是个好消息,不用运行APP就可以下载和上传,这样更节约手机电量。

2.能够暂停和恢复网络操作。不需要使用NSOperation就可以实现暂停、继续、重启等操作。

3.可配置的容器。

4.可以子类化并且可以设置私有存储方式。可以修改数据的存储方式和存储位置。

5.改进了授权处理机制。

6.代理更强大。

7.通过文件系统上传和下载。

  好了,进入整体开始我们的实战,开发一个小的APP叫《ByteClub》。这篇文章的实战我是参考国外的网站做的,原文《NSURLSession Tutorial》,地址:http://www.raywenderlich.com/51127/nsurlsession-tutorial。觉得它有点啰嗦,英文好的也可以看原文。

我没有去原文翻译它,参考它做完例子之后,我按照自己的思路写的本教程。

准备工作

1.如果你打算跟我一起动手做的话,您需要一个FQ工具,因为我需要使用dropbox(类似百度云盘)做http网络服务器,它在国内被墙掉了?,我使用的是lantern.下载地址:http://pan.baidu.com/s/1hqhQqHI。下载完记得一定要安装和运行起来。

2.在dropbox网站注册成为开发者,然后创建一个APP。Dropbox开发者应用注册地址:https://www.dropbox.com/developers/apps。

3.然后下载dropbox for mac,我自己准备好了安装文件DropboxInstaller.dmg,下载地址:http://pan.baidu.com/s/1sjDvZNB。然后安装,安装好后在跟目录下创建byteclub的目录。如图:

4.请在byteclub目录中,随便创建或者复制进来几个文件,然后会同步到服务器上,然后我们的第一步开发工作,就是从服务器读取到这些文件的文件名。

5.然后再下载起始项目,代码把UI界面以及dropbox的http接口做好了封装,以便我们专注于NSURLSession部分的实战和学习。起始项目代码下载地址:http://pan.baidu.com/s/1mg8M2Vm。

6.如果您想查看最终效果,可以下载我实战完成后的代码。下载地址:http://pan.baidu.com/s/1sj48BAP

项目完成后的效果图:

您可以先稍微熟悉下初始项目。

开工干活

第一阶段:读取Dropbox的跟目录文件名,并显示。

1.打开Dropbox.m将您的apiKey和appSecret,appFolder设置进去,前两者认证需呀,后者是我们在准备阶段在Dropbox创建的目录,比如我的设置为:

static NSString *apiKey = @"rctz909lpd47vyq";
static NSString *appSecret = @“odz1qfezg4ij3pz";
NSString * const appFolder = @“byteclub";

然后你可以运行看看,按照引导信息,输入您在dropbox的账号信息,然后应该就可以认证通过了。

2.在NotesViewController.m文件中添加一个会话属性,用于保存我们的会话。

/***   会话*/
@property (nonatomic, strong) NSURLSession *session;

3.在initWithStyle:前面添加另外一个初始化方法:

- (instancetype)initWithCoder:(NSCoder *)aDecoder
{self = [super initWithCoder:aDecoder];//下面内容为创建会话if (self) {//会话配置,这里配置为短暂配置,还有默认配置和后台配置NSURLSessionConfiguration *config = [NSURLSessionConfiguration ephemeralSessionConfiguration];//配置请求头[config setHTTPAdditionalHeaders:@{@"Authorization":[Dropbox apiAuthorizationHeader]}];//初始化会话_session = [NSURLSession sessionWithConfiguration:config];}return self;
}

4.找到notesOnDropbox:方法,然方法内输入如下代码:

//显示加载提示[UIApplication sharedApplication].networkActivityIndicatorVisible = YES;//获取你的Dropbox的根目录NSURL *url = [Dropbox appRootURL];//创建数据任务,这个方法主要用来请求HTTP的GET方法,并返回NSData对象,我们需要将数据再解析成我们需要的数据NSURLSessionDataTask *dataTask = [self.session dataTaskWithURL:url completionHandler:^(NSData * _Nullable data, NSURLResponse * _Nullable response, NSError * _Nullable error) {if (!error) {// 响应状态代码为200,代表请求数据成功,判断成功后我们再进行数据解析NSHTTPURLResponse *httpResp = (NSHTTPURLResponse*) response;if (httpResp.statusCode == 200) {NSError *jsonError;//解析NSData数据NSDictionary *notesJSON =[NSJSONSerialization JSONObjectWithData:dataoptions:NSJSONReadingAllowFragmentserror:&jsonError];NSMutableArray *notesFound = [[NSMutableArray alloc] init];if (!jsonError) {                    // 获取contents键值,文件路径保存在这里NSArray *contentsOfRootDirectory = notesJSON[@"contents"];for (NSDictionary *data in contentsOfRootDirectory) {if (![data[@"is_dir"] boolValue]) {DBFile *note = [[DBFile alloc] initWithJSONData:data];[notesFound addObject:note];}}//排序[notesFound sortUsingComparator:^NSComparisonResult(id obj1, id obj2) {return [obj1 compare:obj2];}];self.notes = notesFound;// NSURLSession的方法是在异步执行的,所以更新UI回到主线程dispatch_async(dispatch_get_main_queue(), ^{[UIApplication sharedApplication].networkActivityIndicatorVisible = NO;[self.tableView reloadData];});}}}}];//启动任务[dataTask resume];

  注释已经比较清晰,如果我们查看Dropbox的文档就会发现,私用这个URL返回的数据就是json数据,数据格式如下:

{"hash": "6a29b68d106bda4473ffdaf2e94c4b61","revision": 73052,"rev": "11d5c00e1cf6c","thumb_exists": false,"bytes": 0,"modified": "Sat, 10 Aug 2013 21:56:50 +0000","path": "/byteclub","is_dir": true,"icon": "folder","root": "dropbox","contents": [{"revision": 73054,"rev": "11d5e00e1cf6c","thumb_exists": false,"bytes": 16,"modified": "Sat, 10 Aug 2013 23:21:03 +0000","client_mtime": "Sat, 10 Aug 2013 23:21:02 +0000","path": "/byteclub/test.txt","is_dir": false,"icon": "page_white_text","root": "dropbox","mime_type": "text/plain","size": "16 bytes"}],"size": "0 bytes"}

  dropbox服务器的返回状态码有如下一些:

400 –代表参数有误.

401 – token错误或过期.

403 – 错误 OAuth 请求

404 – 请求的文件和目录不存在

405 – 请求方法错误,一般我们只使用get 和post

429 –程序请求次数过多

503 –请再次尝试

507 –使用Dropbox空间超过配额限制

5xx – 服务器错误

5.运行一下看看效果,我的效果是这样的:

第一阶段的实战完成,你可以先复习一下内容,然后再进行第二阶段的实战。

第二阶段的实战

  通过APP输入内容,并通过文件的形式保存到Dropbox服务器并然后显示。

1.点击右上角的“+”按钮,跳转到添加Notes界面,你可以输入内容,但目前没什么作用,我们需要实现这些功能。打开NotesViewController.m文件,找到prepareForSegue:sender:跳转方法,在代码showNote.delegate = self后添加下面一行代码,将会话session传递到新的页面,这样我们就可以在新的页面使用同一个会话了:

//传递会话showNote.session = _session;

2.找到新页面所属类的实现文件NoteDetailsViewController.m文件,找到 (IBAction)done:(id)sender方法,这是我们点击done按钮需要执行的方法,替换为如下代码:

- (IBAction)done:(id)sender
{// must contain text in textviewif (![_textView.text isEqualToString:@""]) {// check to see if we are adding a new noteif (!self.note) {DBFile *newNote = [[DBFile alloc] init];newNote.root = @"dropbox";self.note = newNote;}_note.contents = _textView.text;_note.path = _filename.text;// - 上传文件到 DROPBOX - //// 获取需要上传文件的路径NSURL *url = [Dropbox uploadURLForPath:_note.path];// 创建请求,这里使用了put方法NSMutableURLRequest *request =[[NSMutableURLRequest alloc] initWithURL:url];[request setHTTPMethod:@"PUT"];//数据NSData *noteContents = [_note.contents dataUsingEncoding:NSUTF8StringEncoding];// 上传任务,NSURLSessionUploadTask支持文件,NSData,数据流stream的类型数据上传NSURLSessionUploadTask *uploadTask = [_sessionuploadTaskWithRequest:requestfromData:noteContentscompletionHandler:^(NSData *data,NSURLResponse *response,NSError *error){//根据HTTP返回的代号确定是否成功,200代表成功,成功后我调用代理方法NSHTTPURLResponse *httpResp = (NSHTTPURLResponse*) response;if (!error && httpResp.statusCode == 200) {[self.delegate noteDetailsViewControllerDoneWithDetails:self];} else {// alert for error saving / updating note}}];// 必须要的动作,启动任务[uploadTask resume];} else {UIAlertView *noTextAlert = [[UIAlertView alloc] initWithTitle:@"输入为空"message:@"总得输入点啥吧,亲"delegate:nilcancelButtonTitle:@"好"otherButtonTitles:nil];[noTextAlert show];}
}

3.打开NoteDetailsViewController.m方法,找到方法retreiveNoteText:,替换为如下内容:

-(void)retreiveNoteText
{// 根据Dropbox API设置要查看的note的请求路径NSString *fileApi =@"https://api-content.dropbox.com/1/files/dropbox";NSString *escapedPath = [_note.pathstringByAddingPercentEscapesUsingEncoding:NSUTF8StringEncoding];NSString *urlStr = [NSString stringWithFormat: @"%@/%@",fileApi,escapedPath];NSURL *url = [NSURL URLWithString: urlStr];[UIApplication sharedApplication].networkActivityIndicatorVisible = YES;// 执行下载数据任务[[_session dataTaskWithURL:url completionHandler:^(NSData *data, NSURLResponse *response, NSError *error) {if (!error) {NSHTTPURLResponse *httpResp = (NSHTTPURLResponse*) response;if (httpResp.statusCode == 200) {// 数据转字符串NSString *text =[[NSString alloc]initWithData:dataencoding:NSUTF8StringEncoding];dispatch_async(dispatch_get_main_queue(), ^{[UIApplication sharedApplication].networkActivityIndicatorVisible = NO;self.textView.text = text;});} else {// 处理错误的响应 //}} else {// 处理意外错误 //}// 一定要创建任务后启动哦}] resume];}

4.运行看看,比如输入内容,点击done按钮,过一会儿你查看下你的byteclub目录,应该会创建一个新的文件。我的运行效果是这样的:

  好了,我们的第二阶段任务就完成,还是建议您复习一下刚才的内容,然后我们开始第三阶段的实战。

第三阶段

使用NSURLSessionTask的代理方法发送图片到dropbox

1.请在byteclub目录下新建一个photos目录,然后拖一些你的图片到里面来,等待一会儿,图片应该就会上传完。

2.打开PhotosViewController.m,找到tableView:cellForRowAtIndexPath:方法,替换为下面内容:

tableView:cellForRowAtIndexPath:

3.相同文件,找到refreshPhotos方法,替换为下面内容:

 refreshPhotos:

4.休息一下,运行看看,应该可以看到图片加载了,我的效果如图:

  好了,现在我做上传图片的操作,并通过NSURLSessionDelegate和NSURLSessionTaskDelegate来帮助我们了解上传的状态和进度。

5.修改PhotosViewController.m使其遵守NSURLSessionTaskDelegate代理协议,代码如图:

@interface PhotosViewController ()<UITableViewDelegate, UITableViewDataSource, UIImagePickerControllerDelegate, UINavigationControllerDelegate, NSURLSessionTaskDelegate>

6.添加如下属性,用于保存上传任务:

@property (nonatomic, strong) NSURLSessionUploadTask *uploadTask;

7.修改uploadImage:方法,替代为如下内容:

 uploadImage:

8.最类最后面添加NSURLSessionTaskDelegate的两个方法实现:

 NSURLSessionTaskDelegate 方法

9.找到cancelUpload:方法,当我们点击cancel取消时会调用此方法,这里我们需要取消上传任务:

// 停止上传
- (IBAction)cancelUpload:(id)sender
{//取消上传任务if (_uploadTask.state == NSURLSessionTaskStateRunning) {[_uploadTask cancel];}}

10.哈哈,大功告成,运行一下看看效果吧

  至此我通过三篇文章介绍了NSULRSession套件的原理,和它的常用类,然后通过一个实战例子告诉大家NSURLSession如何使用。谢谢大家!

欢迎大家关注我的微信公众号:丁丁的coding日记

转载于:https://my.oschina.net/hejunbinlan/blog/686791

NSURLSESSION使用实战教程相关推荐

  1. PyTorch 高级实战教程:基于 BI-LSTM CRF 实现命名实体识别和中文分词

    20210607 https://blog.csdn.net/u011828281/article/details/81171066 前言:译者实测 PyTorch 代码非常简洁易懂,只需要将中文分词 ...

  2. ArcGIS水文分析实战教程(9)雨量计算与流量统计

    ArcGIS水文分析实战教程(9)雨量计算与流量统计 本章导读:降水是水文循环中重要的一环,降水包括雨.雪.雾.露.雹等,本章介绍的是降雨的环节.通过雨量站与插值的方式,实现雨量的空间分布就算,为水文 ...

  3. 宏基因组分析实战教程1. 背景知识

    上次我写的学习经验和推荐的教程--<微生物组入门必读+宏基因组实操课程=新老司机赶快上车>,小伙伴们当天阅读破2700+人次,3.5天破3000+,达到了宏基因组快车满三千人发车的要求.我 ...

  4. js模板字符串自定义类名_【Vue.js 入门到实战教程】07Vue 组件注册 | 基本使用和组件嵌套...

    来源 | https://xueyuanjun.com/post/21929除了前面介绍的基本语法之外,Vue.js 还支持通过组件构建复杂的功能模块,组件可以称得上是 Vue.js 的灵魂,是 Vu ...

  5. python商业爬虫教程_廖雪峰老师的Python商业爬虫课程 Python网络爬虫实战教程 体会不一样的Python爬虫课程...

    廖雪峰老师的Python商业爬虫课程 Python网络爬虫实战教程 体会不一样的Python爬虫课程 1.JPG (53.51 KB, 下载次数: 1) 2019-8-9 08:15 上传 2.JPG ...

  6. Swift游戏开发实战教程(大学霸内部资料)

    Swift游戏开发实战教程(大学霸内部资料) 试读下载地址:http://pan.baidu.com/s/1sj7DvQH 介绍:本教程是国内第一本Swift游戏开发专向资料. 本教程详细讲解记忆配对 ...

  7. python教程下载地址-最新python实战教程网盘下载地址

    原标题:最新python实战教程网盘下载地址 Python在程序员中始终流行:40%的受访者都会学习,44%的受访者每周都会学习.目前技术领域最热点的技术排名,排在前一位的是:Python.Pytho ...

  8. python3项目-终于找到python3项目实战教程

    列表的元素是可以变动的,比如增加.删除.修改,不过需要注意的是,列表的元素不是基本数据类型,都是一个个的标识符引用对象.以下是小编为你整理的python3项目实战教程 先定义一个列表 a = [123 ...

  9. yolov5训练_YoloV5模型训练实战教程:Kaggle全球小麦检测竞赛

    写在前面 前段时间参加了Kaggle的一个目标检测竞赛,比赛后期因为工作较繁忙就搁置了,但仍然获得了铜牌(前10%).因此在这里想跟大家分享下自己的方案,希望能帮助大家更好的了解目标检测这一经典的计算 ...

最新文章

  1. C++——包装器std::function与绑定器std::bind
  2. oracle 查询无限开始,Oracle无限分级下查询指定分类下所有子分类Sql
  3. 号外号外!RancherOS v1.2.0发布啦!
  4. nodejs 利用zip-local模块压缩文件夹
  5. 【JavaEE企业应用实战学习记录】struts配置文件详细解析
  6. 度量术语之二:应用类和开发类生产率(实际度量案例)
  7. UVALive 4764 dp
  8. 作者:靳小龙,中国科学院计算技术研究所副研究员,博士生导师。
  9. 安装Magento的系统需求
  10. 分组分页连接查询子查询9202-0422
  11. 佛系青蛙外挂横行,20 元可买 21 亿无限三叶草
  12. numpy——flat与flatten
  13. token会被截取吗_新手剪辑:如何截取视频的某个片段?
  14. java中修改和删除的单词_Java 解惑: 你能通过改变一个单词来解决这个bug吗?
  15. python爬微博个人信息_新浪微博数据爬取Part 1:用户个人信息
  16. python-css偏移反爬(一)
  17. mac抹掉磁盘重装系统未能与服务器取得联系_干活!苹果电脑安装mac系统详细教程...
  18. 超 82% 的 GitHub 代码是重复的,还不是 Forked 而来。
  19. 在AWS Lambda上部署标准FFmpeg工具——Docker方案
  20. windows当中python的安装和环境部署,和数据类型,并且在linux当中安装python是windows当中的pycharm基于linux可以运行

热门文章

  1. android 行高和字号之间关系,字号与行高
  2. matlab工具箱分析关节力矩,在matlab工具箱中,以下选项中哪个方法是用来计算动力学力矩?...
  3. 实施工程师的必要条件
  4. Vivado HLS 入门实验
  5. Topcoder SRM 700 1000pts:AnyNumber(DP)
  6. 计算机教育学专业考研科目,计算机考研科目和专业
  7. 计算机网络——域名系统(DNS)
  8. cudnn 版本查看
  9. Partial-ReID
  10. 穆迪ESG解决方案事业部旗下公司V.E就西班牙王国的主权绿色债券框架提供第二方意见