Я конвертирую приложение iOS из NSURLConnection в NSURLSession.
Сервер взаимодействует с использованием как https (сертификат, подписанный признанным ЦС), так и базовая аутентификация.
Вместо использования блоков завершения для возврата данных я использую пользовательские делегаты. Я видел в другом месте, что использование пользовательских делегатов означает, что я должен отвечать на AuthenticationChallenges, а не полагаться на CredentialStorage (но это не работает, но это еще одна проблема).
Моя проблема заключается в том, что вызов возникает один раз для ServerTrust, но не вызван снова для HttpBasic Authentication. Итак, мои сеансы заканчиваются.
Я пробовал использовать блоки завершения для 'defaultSession dataTaskWithRequest', а не пользовательские делегаты, чтобы проверить, не могу ли я пройти мимо этого момента, но это не имеет значения. Я также попытался использовать CredentialStorage для учетных данных HttpBasic, но, как упоминалось выше, не было радости.
Это меня насторожило. Любые идеи?
(void)URLSession:(NSURLSession *)connection
// task:(NSURLSessionTask *)task
didReceiveChallenge:(NSURLAuthenticationChallenge *)challenge
completionHandler:(void (^)(NSURLSessionAuthChallengeDisposition disposition, NSURLCredential * __nullable credential))completionHandler
{
if ([challenge.protectionSpace.authenticationMethod isEqualToString:NSURLAuthenticationMethodServerTrust])
{
#if 1 && defined(DEBUG)
NSLog (@"didReceiveChallenge: Using SSL");
#endif // DEBUG
if ([challenge.protectionSpace.host isEqualToString:HOST])
{
#if 1 && defined(DEBUG)
NSLog (@"didReceiveChallenge: Using Protection Space Host - %@", HOST);
#endif // DEBUG
[challenge.sender useCredential:[NSURLCredential credentialForTrust:challenge.protectionSpace.serverTrust] forAuthenticationChallenge:challenge];
}
else
{
[challenge.sender continueWithoutCredentialForAuthenticationChallenge:challenge];
}
}
else
if ([challenge.protectionSpace.authenticationMethod isEqualToString:NSURLAuthenticationMethodHTTPBasic] ||
[challenge.protectionSpace.authenticationMethod isEqualToString:NSURLAuthenticationMethodHTTPDigest])
{
#if 1 && defined(DEBUG)
NSLog (@"didReceiveChallenge: (Basic / Digest) #%ld - user: %@, password: %@",
(long)[challenge previousFailureCount], USERNAME, PASSWORD);
#endif // DEBUG
if ([challenge previousFailureCount] == 0)
{
#if 1 && defined(DEBUG)
NSLog (@"didReceiveChallenge: previousFailureCount == 0");
#endif // DEBUG
NSURLCredential *newCredential;
newCredential = [NSURLCredential credentialWithUser:USERNAME
password:PASSWORD
persistence:NSURLCredentialPersistenceForSession];
[[challenge sender] useCredential:newCredential forAuthenticationChallenge:challenge];
}
else
{
[[challenge sender] cancelAuthenticationChallenge:challenge];
// inform the user that the user name and password
// in the preferences are incorrect
#if 1 && defined(DEBUG)
NSLog (@"didReceiveChallenge: Failed Authentication");
#endif // DEBUG
// ...error will be handled by connection didFailWithError
}
}
#ifdef DEBUG
else
{
NSLog(@"didReceiveChallenge: Not handled!");
}
#endif // DEBUG
}