Question

This seems weird. I can't seem to seem to successfully set an NSURLSession's delegateQueue on creation.

- (void)viewDidLoad
{
    [super viewDidLoad];

    NSOperationQueue *queue = [[NSOperationQueue alloc] init];
    queue.maxConcurrentOperationCount = 5;

    NSLog(@"The queue before: %@", queue);
    NSLog(@"Max op Count before: %i", queue.maxConcurrentOperationCount);

    NSURLSession *session = [NSURLSession sessionWithConfiguration:nil
                                                          delegate:self
                                                     delegateQueue:queue];

    NSLog(@"The queue after: %@", session.delegateQueue);
    NSLog(@"Max op Count after : %i", session.delegateQueue.maxConcurrentOperationCount);
}

This results in the following output.

The queue before: <NSOperationQueue:   0x16d99160>{name = 'NSOperationQueue 0x16d99160'}
Max op Count before: 5
The queue after: <NSOperationQueue: 0x16d77a50>{name = 'NSOperationQueue 0x16d77a50'}
Max op Count after : 1

It looks like my delegateQueue is being ignored. I've tried on the device as well as on the simulator. I've haven't found any documentation which would explain this. Does anyone have any insight?

Was it helpful?

Solution

It looks like, despite what the getter for delegateQueue says, the NSURLSession is indeed using your NSOperationQueue. I added KVO for the "operations" property on the queue:

[queue addObserver:self forKeyPath:@"operations" options:NSKeyValueObservingOptionNew context:NULL];

And added the following method:

- (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context
{
    NSLog(@"%@%@", object, change);
    NSOperationQueue *queue = (NSOperationQueue *)object;

    NSLog(@"The queue in KVO: %@", queue);
    NSLog(@"Max op Count in KVO: %i", queue.maxConcurrentOperationCount);

    NSLog(@"%@", self.session.delegateQueue);

}

And it prints:

2013-09-29 07:45:13.751 sotest1[17214:1403] <NSOperationQueue: 0x895e0c0>{name = 'NSOperationQueue 0x895e0c0'}
2013-09-29 07:45:13.757 sotest1[17214:4207] <NSOperationQueue: 0x98a0940>{name = 'NSOperationQueue 0x98a0940'}{
    kind = 1;
    new =     (
        "<NSBlockOperation: 0x9a52370>"
    );
}
2013-09-29 07:45:13.757 sotest1[17214:4207] The queue in KVO: <NSOperationQueue: 0x98a0940>{name = 'NSOperationQueue 0x98a0940'}
2013-09-29 07:45:13.757 sotest1[17214:4207] Max op Count in KVO: 5

So you can see the delegate does indeed get processed by your queue, despite the fact that the getter says otherwise. Weird.

Btw, the way you're doing it is also exactly AFNetworking does it, which is generally a good sign: https://github.com/AFNetworking/AFNetworking/blob/master/AFNetworking/AFURLSessionManager.m#L287

OTHER TIPS

I confirm the problem on my side I tried to set a queue of 1 element as you did using the maxConcurrentOperationCount=1 on the session I see several tasks running in the same time as described by the logged below in the (URLSession:didWriteData:totalBytesWritten):

NSLog(@"Download %.2f%% task=%d - operationInQueue=%d maxOperation=%d ", result, [downloadTask taskIdentifier], [self.bkgQueue operationCount],[self.bckQueue maxConcurrentOperationCount]);

Download 1.80% task=2 - operationInQueue=2 maxOperation=1 
Download 1.15% task=1 - operationInQueue=1 maxOperation=1 
Download 1.49% task=1 - operationInQueue=1 maxOperation=1 
Download 1.51% task=1 - operationInQueue=1 maxOperation=1 
Download 1.14% task=0 - operationInQueue=1 maxOperation=1 
Download 3.90% task=2 - operationInQueue=2 maxOperation=1 
Download 1.14% task=0 - operationInQueue=1 maxOperation=1 
Download 1.85% task=1 - operationInQueue=1 maxOperation=1 
Download 1.87% task=1 - operationInQueue=1 maxOperation=1 

I also tried to increase this number and a count on my queue=1. It seems it is managing by himself the queue.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top