NSURLSessionTask 从不回调,错误信息是在握手过程中对等方断开连接。发送 errSSLClosedNoNotify(-9816) 警报

dan*_*zjx 8 macos https ios nsurlsession

代码:

#pragma mark - Post data
-(void)postData:(NSData *)data withUrl:(NSString*)urlStr completion:(void (^)(NSError *error, NSData *data))callback
    {
        NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:[NSURL URLWithString:urlStr] cachePolicy:NSURLRequestUseProtocolCachePolicy timeoutInterval:OC_SEND_TIMEOUT_INTERVAL];
        request.HTTPMethod = @"POST";
        [request setValue:@"application/json" forHTTPHeaderField:@"Content-Type"];
        [request setValue:[@([data length]) stringValue] forHTTPHeaderField:@"Content-Length"];
        [request setValue:self.userAgent forHTTPHeaderField: @"User-Agent"];
        request.HTTPBody = data;

        NSURLSessionConfiguration *configuration = [NSURLSessionConfiguration defaultSessionConfiguration];
        NSDictionary *proxyDict = @{
                                    @"HTTPEnable"  : [NSNumber numberWithInt:1],
                                    (NSString *)kCFStreamPropertyProxyLocalBypass  : @"*.*.*.*",
                                    @"HTTPSEnable" : [NSNumber numberWithInt:1],
                                    (NSString *)kCFStreamPropertyProxyLocalBypass  : @"*.*.*.*"
                                    };
        configuration.connectionProxyDictionary = proxyDict;

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

        NSURLSessionTask *task = [session dataTaskWithRequest:request completionHandler:^(NSData *rdata, NSURLResponse *response, NSError *error){
            callback(error, rdata);
            [session finishTasksAndInvalidate];
        }];
        [task resume];
}

-(void) URLSession:(NSURLSession *)session didReceiveChallenge:(NSURLAuthenticationChallenge *)challenge completionHandler:(void (^)(NSURLSessionAuthChallengeDisposition, NSURLCredential * _Nullable))completionHandler{
    NSURLSessionAuthChallengeDisposition disposition = NSURLSessionAuthChallengePerformDefaultHandling;
    __block NSURLCredential *credential = nil;

    if ([challenge.protectionSpace.authenticationMethod isEqualToString:NSURLAuthenticationMethodServerTrust]) {
        BOOL ret = [self.securityPolicy evaluateServerTrust:challenge.protectionSpace.serverTrust forDomain:challenge.protectionSpace.host];

        if (ret) {
            credential = [NSURLCredential credentialForTrust:challenge.protectionSpace.serverTrust];
            if (credential) {
                disposition = NSURLSessionAuthChallengeUseCredential;
            } else {
                disposition = NSURLSessionAuthChallengePerformDefaultHandling;
            }
        } else {
            LOG_ERROR(USTAG, @"evaluate server trust failed!");
            disposition = NSURLSessionAuthChallengeCancelAuthenticationChallenge;
        }
    } else {
        disposition = NSURLSessionAuthChallengePerformDefaultHandling;
    }

    if (completionHandler) {
        completionHandler(disposition, credential);
    }
}
<!-- end snippet -->
Run Code Online (Sandbox Code Playgroud)

错误信息:

#pragma mark - Post data
-(void)postData:(NSData *)data withUrl:(NSString*)urlStr completion:(void (^)(NSError *error, NSData *data))callback
    {
        NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:[NSURL URLWithString:urlStr] cachePolicy:NSURLRequestUseProtocolCachePolicy timeoutInterval:OC_SEND_TIMEOUT_INTERVAL];
        request.HTTPMethod = @"POST";
        [request setValue:@"application/json" forHTTPHeaderField:@"Content-Type"];
        [request setValue:[@([data length]) stringValue] forHTTPHeaderField:@"Content-Length"];
        [request setValue:self.userAgent forHTTPHeaderField: @"User-Agent"];
        request.HTTPBody = data;

        NSURLSessionConfiguration *configuration = [NSURLSessionConfiguration defaultSessionConfiguration];
        NSDictionary *proxyDict = @{
                                    @"HTTPEnable"  : [NSNumber numberWithInt:1],
                                    (NSString *)kCFStreamPropertyProxyLocalBypass  : @"*.*.*.*",
                                    @"HTTPSEnable" : [NSNumber numberWithInt:1],
                                    (NSString *)kCFStreamPropertyProxyLocalBypass  : @"*.*.*.*"
                                    };
        configuration.connectionProxyDictionary = proxyDict;

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

        NSURLSessionTask *task = [session dataTaskWithRequest:request completionHandler:^(NSData *rdata, NSURLResponse *response, NSError *error){
            callback(error, rdata);
            [session finishTasksAndInvalidate];
        }];
        [task resume];
}

-(void) URLSession:(NSURLSession *)session didReceiveChallenge:(NSURLAuthenticationChallenge *)challenge completionHandler:(void (^)(NSURLSessionAuthChallengeDisposition, NSURLCredential * _Nullable))completionHandler{
    NSURLSessionAuthChallengeDisposition disposition = NSURLSessionAuthChallengePerformDefaultHandling;
    __block NSURLCredential *credential = nil;

    if ([challenge.protectionSpace.authenticationMethod isEqualToString:NSURLAuthenticationMethodServerTrust]) {
        BOOL ret = [self.securityPolicy evaluateServerTrust:challenge.protectionSpace.serverTrust forDomain:challenge.protectionSpace.host];

        if (ret) {
            credential = [NSURLCredential credentialForTrust:challenge.protectionSpace.serverTrust];
            if (credential) {
                disposition = NSURLSessionAuthChallengeUseCredential;
            } else {
                disposition = NSURLSessionAuthChallengePerformDefaultHandling;
            }
        } else {
            LOG_ERROR(USTAG, @"evaluate server trust failed!");
            disposition = NSURLSessionAuthChallengeCancelAuthenticationChallenge;
        }
    } else {
        disposition = NSURLSessionAuthChallengePerformDefaultHandling;
    }

    if (completionHandler) {
        completionHandler(disposition, credential);
    }
}
<!-- end snippet -->
Run Code Online (Sandbox Code Playgroud)

信息.plist:

    <key>NSAppTransportSecurity</key>
<dict>
    <key>NSAllowsArbitraryLoads</key>
    <true/>
    <key>NSExceptionDomains</key>
    <dict>
        <key>domain-1</key>
        <dict>
            <key>NSExceptionMinimumTLSVersion</key>
            <string>TLSv1.0</string>
        </dict>
        <key>domain-2</key>
        <dict>
            <key>NSExceptionMinimumTLSVersion</key>
            <string>TLSv1.0</string>
        </dict>
        <key>domain-3</key>
        <dict>
            <key>NSExceptionMinimumTLSVersion</key>
            <string>TLSv1.0</string>
        </dict>
    </dict>
</dict>
Run Code Online (Sandbox Code Playgroud)