2013-10-16 38 views
5

我需要连接到我的服务器才能获得一些JSON数据,我必须同时支持iOS 6iOS 7NSURLSession或NSURLConnection - iOS 6支持

我应该创建两个类?其中NSURLSessioniOS 7,NSURLConnectioniOS 6?或者我应该只为他们两个使用NSURLConnection

+0

检查这个链接看NSURLSession上的一个很好的教程:http://www.raywenderlich.com/51127/nsurlsession-tutorial – whyoz

回答

3

将通过创建两个单独的类,基本上做同样的事情得到什么好处?如果你不能使用NSURLSession,因为它仅在iOS 7中受支持,并且你可以使用NSURLConnection获得相同的功能,NSURLConnection可以在两者中使用,然后只需使用NSURLConnection。你将有更少的代码来维护。

+0

这正是我的想法,但不应该总是使用最新的类?或者,我认识到自己是一件坏事? – yoeriboven

+1

那么在使用酷酷的新API和支持较老的操作系统之间总是有一个权衡。新的API非常好,它可以帮助您避免在旧版本中执行额外的工作。但是,如果实施新的API意味着更多的工作(尤其是重复的工作),那么我将不得不传递它。 – Brian

+0

似乎并不是这种情况......如果您需要持续进行会话,您似乎需要两者,或者每次提出请求时都需要坚持一个新的会话,或者至少要通过凭证过程而不是坚持,取决于你需要连接多长时间。 – whyoz

0

如果您必须使用NSURLCredentialPersistenceForSession才能进入Windows身份验证网络,那么使用NSURLConnection会为您创建多个问题。我经历的痛苦,现在和已经开始,我需要同时支持iOS的7。基本上,如果你使用NSURLConnectionwillSendRequestForAuthenticationChallenge结论,你会发现,在搭载iOS 7,您的会话将用一记结束的这自己的(似乎是30秒的思路)。所以,如果你必须坚持证书访问更多的SOAP或其他,欢迎来到恐怖圆顶!如果我找到顺利的解决方案,我会用代码向你报告。

3

伟大的问题。事实上,我有同样的问题,并研究了一下,我认为这是一个使用协议(a.k.a.其他语言的接口)的好地方。这是基于从着名的“四人帮”模式书引用的“程序到接口,而不是实现”。我认为最好是为未来编写代码,所以如果他们决定贬低某些东西(这里不是这种情况,但你永远不知道),我永远不会受到攻击。

不是编写类,而是编写一个定义您想要使用的方法的协议,然后创建2个实现这些方法的不同类。在你的应用程序中,你将创建一个指针,指向任何实现所有协议方法的类,然后每个实现类可以使用他们想要实现的任何框架/库/其他代码。

举个例子,你可以创建这样的服务器协议:

// Server.h 
@protocol Server <NSObject> 
@required 
- (void)callService:(NSString *)service withData:(NSData *)data; 
@end 

,然后创建一个RestServer类是这样的:

// RestServer.h 
#import "Server.h" 
@interface RestServer : NSObject <Server> 
@end 

// RestServer.m 
#import "RestServer.h" 
@implementation RestServer 
- (void)callService:(NSString *)service withData:(NSData *)data { 
// Code using REST 
} 
@end 

,然后创建SoapServer的另一个类:

// SoapServer.h 
#import "Server.h" 
@interface SoapServer : NSObject <Server> 
@end 

// SoapServer.m 
#import “SoapServer.h" 
@implementation SoapServer 
- (void)callService:(NSString *)service withData:(NSData *)data { 
// Code using SOAP 
} 
@end 

将您的主应用程序编码为仅使用指向界面的指针,现在您可以切换类•不用改变你的主代码:

// SomeViewController.m 
#import “Server.h” 
#import “RestServer.h” 
#import “SoapServer.h” 
… 
- (void)someMethod() { 
    id<Server> myServer; 

    if ([self shouldIUseSoap]) 
     myServer = [[SoapServer alloc] init]; 
    else 
     myServer = [[RestServer alloc] init]; 

    [myServer callService:@"loginUser" withData:[self getData]]; 
} 

现在你可以改变服务器类,只要你想,从来没有必须去追捕所有在你的代码,你做出callService呼叫的地方:withData :.这是对接口进行编程的好处!

我使用了Rest vs Soap,因为我觉得Objective-C更新的人可能会更好地理解,但在你的情况下,你可能会有一个ConnectionServer vs SessionServer或类似的东西。

上编程接口的另一个良好的读/协议可以在这里找到:https://stackoverflow.com/a/384067/504873

0

在写作的时候,NSURLConnection的已被弃用,在OS X 10.11和iOS 9.0,但我的应用程序需要支持OS X 10.7和iOS 6. 因此,现在您必须为正在进行的项目使用NSURLSession,但也支持现在已弃用的NSURLConnection类,以支持旧版OS!

我会这些天投票TenaciousJay解决方案与NSURLConnection类实现周围的编译器警告抑制。

#pragma GCC diagnostic push 
#pragma GCC diagnostic ignored "-Wdeprecated-declarations" 
     /* NSURLConnection code here */ 
#pragma GCC diagnostic pop 

你,你会通过创建两个单独的类,做中所获得的利益基本上是相同的事情是,你最终可以切断老,过时的解决方案,当你终于可以放弃对旧的操作系统版本的支持。

我使用一类或其他代码的决定不会基于某些类的属性,但对结果的宏,如:

#define SYSTEM_VERSION_GREATER_THAN_OR_EQUAL_TO(v) ([[[UIDevice currentDevice] systemVersion] compare:v options:NSNumericSearch] != NSOrderedAscending) 

针对iOS或OS X:

NSString *systemVersion = nil; 
     if ([[NSProcessInfo processInfo] respondsToSelector:NSSelectorFromString(@"operatingSystemVersion")]) { 
      NSOperatingSystemVersion operatingSystemVersion = [[NSProcessInfo processInfo] operatingSystemVersion]; 
      systemVersion  = [NSString stringWithFormat:@"%ld.%ld.%ld", (long)operatingSystemVersion.majorVersion, (long)operatingSystemVersion.minorVersion, (long)operatingSystemVersion.patchVersion]; 
     } else { 
      SInt32 versionMajor=0, versionMinor=0, versionPatch=0; 
#pragma GCC diagnostic push 
#pragma GCC diagnostic ignored "-Wdeprecated-declarations" 
      Gestalt(gestaltSystemVersionMajor, &versionMajor); 
      Gestalt(gestaltSystemVersionMinor, &versionMinor); 
      Gestalt(gestaltSystemVersionBugFix, &versionPatch); 
#pragma GCC diagnostic pop 
      systemVersion  = [NSString stringWithFormat:@"%ld.%ld.%ld", (long)versionMajor, (long)versionMinor, (long)versionPatch]; 
     } 
     NSLog(@"[Line %d] %s OS X Runtime Version: '%@'", __LINE__, __PRETTY_FUNCTION__, systemVersion);