自己动手写一个iOS网络请求库——降低耦合

开源项目:Pitaya,适合大文件上传的 HTTP 请求库:https://github.com/johnlui/Pitaya

创新互联专注于紫阳企业网站建设,成都响应式网站建设公司,商城网站制作。紫阳网站建设公司,为紫阳等地区提供建站服务。全流程按需开发网站,专业设计,全程项目跟踪,创新互联专业和态度为您提供的服务

本文中,我们将一起降低之前代码的耦合度,并使用适配器模式实现一层独立于底层结构的网络 API,造一个真正的网络请求“库”。

降低耦合度

如何降低耦合度

现在的清汤挂面式的代码虽然便于理解,但是功能单一,代码杂乱。我们一起来分析 NSURLSession 的使用过程:

构造 NSURLRequest

确定 URL

确定 HTTP 方法(GET、POST 等)

添加特定的 HTTP 头

填充 HTTP Body

驱动 session.dataTaskWithRequest 方法,开始请求

具体实施

在 Network 下另外新建一个 NetworkManager 类,将 URL、params、files 等设为成员变量,让他们在构造函数中初始化:

 
 
  1. class NetworkManager { 
  2.  
  3. let method: String! 
  4. let params: Dictionary let callback: (data: NSData!, response: NSURLResponse!, error: NSError!) -> Void 
  5.  
  6. let session = NSURLSession.sharedSession() 
  7. let url: String! 
  8. var request: NSMutableURLRequest! 
  9. var task: NSURLSessionTask! 
  10.  
  11. init(url: String, method: String, params: Dictionary = Dictionary(), callback: (data: NSData!, response: NSURLResponse!, error: NSError!) -> Void) { 
  12. self.url = url 
  13. self.request = NSMutableURLRequest(URL: NSURL(string: url)!) 
  14. self.method = method 
  15. self.params = params 
  16. self.callback = callback 

之后,将上面分析的

1. 确定 URL

2. 确定 HTTP 方法(GET、POST 等)

3. 添加特定的 HTTP 头

4. 填充 HTTP Body

前三步封装到一个 function 中,***一步封装到一个 function 中,然后把驱动 session.dataTaskWithRequest 的代码封装到一个 function 中:
 

 
 
  1. func buildRequest() { 
  2. if self.method == "GET" && self.params.count > 0 { 
  3. self.request = NSMutableURLRequest(URL: NSURL(string: url + "?" + buildParams(self.params))!) 
  4.  
  5. request.HTTPMethod = self.method 
  6.  
  7. if self.params.count > 0 { 
  8. request.addValue("application/x-www-form-urlencoded", forHTTPHeaderField: "Content-Type") 
  9. func buildBody() { 
  10. if self.params.count > 0 && self.method != "GET" { 
  11. request.HTTPBody = buildParams(self.params).nsdata 
  12. func fireTask() { 
  13. task = session.dataTaskWithRequest(request, completionHandler: { (data, response, error) -> Void in 
  14. self.callback(data: data, response: response, error: error) 
  15. }) 
  16. task.resume() 

之后使用一个统一的方法来驱动上面三个 function,完成请求:

 
 
  1. func fire() { 
  2. buildRequest() 
  3. buildBody() 
  4. fireTask() 

同时,不要忘了那三个 parse params 的从 Alamofire 偷来的函数哦,也要放到这个类里面。至此,降低耦合的工作基本完成,接下来我们开始封装“网络API”。

使用适配器模式封装“网络API”

理解适配器模式

适配器模式是设计模式中的一种,很容易理解:我的 APP 需要一个获取某一个 URL 返回的字符串的功能,我现在选择的是 Alamofire,但是正在发展的 Pitaya 看起来不错,我以后想替换成 Pitaya,所以我封装了一层我自己的网络接口,用来屏蔽底层细节,到时候只需要修改这个类,不需要再深入项目中改那么多接口调用了。

适配器模式听起来高大上,其实这是我们在日常编码中非常常用的设计模式。

Do it!

修改 Network 类的代码为:

 
 
  1. class Network{ 
  2. static func request(method: String, url: String, params: Dictionary = Dictionary(), callback: (data: NSData!, response: NSURLResponse!, error: NSError!) -> Void) { 
  3. let manager = NetworkManager(url: url, method: method, params: params, callback: callback) 
  4. manager.fire() 

搞定!

封装多级接口

不带 params 的接口:

 
 
  1. static func request(method: String, url: String, callback: (data: NSData!, response: NSURLResponse!, error: NSError!) -> Void) { 
  2. let manager = NetworkManager(url: url, method: method, callback: callback) 
  3. manager.fire() 

两个 get 接口(带与不带 params):
 

 
 
  1. static func get(url: String, callback: (data: NSData!, response: NSURLResponse!, error: NSError!) -> Void) { 
  2. let manager = NetworkManager(url: url, method: "GET", callback: callback) 
  3. manager.fire() 
  4. static func get(url: String, params: Dictionary, callback: (data: NSData!, response: NSURLResponse!, error: NSError!) -> Void) { 
  5. let manager = NetworkManager(url: url, method: "GET", params: params, callback: callback) 
  6. manager.fire() 

两个 post 接口(带与不带 params):
 

 
 
  1. static func post(url: String, callback: (data: NSData!, response: NSURLResponse!, error: NSError!) -> Void) { 
  2. let manager = NetworkManager(url: url, method: "POST", callback: callback) 
  3. manager.fire() 
  4. static func post(url: String, params: Dictionary, callback: (data: NSData!, response: NSURLResponse!, error: NSError!) -> Void) { 
  5. let manager = NetworkManager(url: url, method: "POST", params: params, callback: callback) 
  6. manager.fire() 

测试接口

修改 ViewController 中的调用代码,测试多级 API:
 

 
 
  1. @IBAction func mainButtonBeTapped(sender: AnyObject) { 
  2. let url = "http://pitayaswift.sinaapp.com/pitaya.php" 
  3.  
  4. Network.post(url, callback: { (data, response, error) -> Void in 
  5. println("POST 1 请求成功") 
  6. }) 
  7. Network.post(url, params: ["post": "POST Network"], callback: { (data, response, error) -> Void in 
  8. let string = NSString(data: data, encoding: NSUTF8StringEncoding) as! String 
  9. println("POST 2 请求成功 " + string) 
  10. }) 
  11.  
  12. Network.get(url, callback: { (data, response, error) -> Void in 
  13. println("GET 1 请求成功") 
  14. }) 
  15. Network.get(url, params: ["get": "POST Network"], callback: { (data, response, error) -> Void in 
  16. let string = NSString(data: data, encoding: NSUTF8StringEncoding) as! String 
  17. println("GET 2 请求成功 " + string) 
  18. }) 
  19.  
  20. Network.request("GET", url: url, params: ["get": "Request Network"]) { (data, response, error) -> Void in 
  21. let string = NSString(data: data, encoding: NSUTF8StringEncoding) as! String 
  22. println("Request 请求成功 " + string) 

运行项目,点击按钮,查看效果:

多级 API 封装成功!
 

文章标题:自己动手写一个iOS网络请求库——降低耦合
网页链接:http://www.shufengxianlan.com/qtweb/news5/194505.html

网站建设、网络推广公司-创新互联,是专注品牌与效果的网站制作,网络营销seo公司;服务项目有等

广告

声明:本网站发布的内容(图片、视频和文字)以用户投稿、用户转载内容为主,如果涉及侵权请尽快告知,我们将会在第一时间删除。文章观点不代表本网站立场,如需处理请联系客服。电话:028-86922220;邮箱:631063699@qq.com。内容未经允许不得转载,或转载时需注明来源: 创新互联