I am working on an app that will connect to different data providers, as I started developing different classes to handle those providers I started seeing similarities between the functionality I needed. so I decided to create a base classs that inherits from NSObject
, and expose some properties and methods on that class that are definitely appearing in all clients.
This is the base class
@interface AhmBaseDataLoader : NSObject {
NSMutableArray *elementsArray;
}
- (void)loadElements:(NSString *)searchValue;
@property (nonatomic, strong) NSArray *Elements;
And I have about four classes inheriting this class, all of them have to
loadElements:(NSString *)searchValue {
//I dO some data work here using NSURL and basic classes
NSData* data = [NSData dataWithContentsOfURL:[NSURL URLWithString:url]];
}
Now so far I've been using basic NSURLSession
work in the sub classes to load the data. This has been working ok so far. This all happens on background threads. the loading http process can be sometimes long and I need to be able to cancel that process sometimes.
So My question is, with this kind of setup, is it beneficial to include afnetworking? I know its very popular and super fast, but I am confused If I did use it would I make my baseloader inherit from AFHTTPSessionManager
, or create one as a property? What would be recommended for my scenario?
AFNetworking is a very good library for networking. If you need something more advanced than basic stuff and you don't want to reimplement them by yourself, it is a good (best?) choice. Note that AF 2.0 is not compatible with older versions of OSX and iOS, so pay attention to which version of AF you use.
About your problem.
I am not a fan of subclassing.
Sometime there are classes you want to subclass (e.g. UIView
, UIViewController
, ...) because they are meant to.
But for more "complete" classes, it is more common to use them. And if you need to customize the behaviour, usually they provide delegate methods.
If I were you I would add a property of type AFHTTPSessionManager
(If you use AF 2.0) in all yours objects
@property (nonatomic, strong) AFHTTPSessionManager *httpSessionManager;
and the loadElementes:
simply use it.
In your AppDelegate
, or where you create your objects, I would create the manager and set it to every object. So something like
AFHTTPSessionManager *httpSessionManager = ... //;
AhmBaseDataLoader *myFirstLoader = [[AhmBaseDataLoader alloc] init];
myFirstLoader. httpSessionManager = httpSessionManager;
EDIT: If you use AF 1.X for compatibility reasons (as I do), you should use AFHTTPClient
instead of AFHTTPSessionManager
EDIT2:
Regarding your first comment.
Your superclass will have the AFHTTPSessionManager
and all your subclasses will have access to it, this is true. And I assume they use it during the loadElements:
method (or any other method in fact).
You superclass can have an init method of course.
I think there can be just one session manager for all the subclasses (correct me if I'm wrong. It uses queue to load data so you don't have to bother about serializing the requests). So I was suggesting that, in the class where you create your subclasses (e.g. your AppDelegate) you create first the session manager and after you set it to all your objects.
For example:
//AppDelegate.m
- (void)applicationDidFinishLaunching:(NSNotification *)aNotification {
...
AFHTTPSessionManager *httpSessionManager = ... //; create the session and configure it
AhmBaseDataLoader *myFirstLoader = [[AhmDerived1DataLoader alloc] init];
myFirstLoader. httpSessionManager = httpSessionManager;
AhmBaseDataLoader *mySecondLoader = [[AhmDerived2DataLoader alloc] init];
mySecondLoader. httpSessionManager = httpSessionManager;
AhmBaseDataLoader *myThirdLoader = [[AhmDerived3DataLoader alloc] init];
myThirdLoader. httpSessionManager = httpSessionManager;
AhmBaseDataLoader *myFourthLoader = [[AhmDerived4DataLoader alloc] init];
myFourthLoader. httpSessionManager = httpSessionManager;
}