Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/cocoa/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
CFHTTPAuthenticationCreateFromResponse无法分析响应 我正在编写IOS代码,用HTTPS代理服务器进行身份验证,并需要使用核心基础API来构造代理授权标头。但是,我在尝试构建有效的CFHTTPAuthenticationRef对象时被阻止_Ios_Cocoa_Http Authentication_Http Proxy_Cfnetwork - Fatal编程技术网

CFHTTPAuthenticationCreateFromResponse无法分析响应 我正在编写IOS代码,用HTTPS代理服务器进行身份验证,并需要使用核心基础API来构造代理授权标头。但是,我在尝试构建有效的CFHTTPAuthenticationRef对象时被阻止

CFHTTPAuthenticationCreateFromResponse无法分析响应 我正在编写IOS代码,用HTTPS代理服务器进行身份验证,并需要使用核心基础API来构造代理授权标头。但是,我在尝试构建有效的CFHTTPAuthenticationRef对象时被阻止,ios,cocoa,http-authentication,http-proxy,cfnetwork,Ios,Cocoa,Http Authentication,Http Proxy,Cfnetwork,收到带有“Proxy Authenticate:Basic realm=example.com”头的“407 Proxy authentication required”响应后,我将调用CFHTTPAuthenticationCreateFromResponse。这将返回无效的CFHTTPAuthenticationRef对象;错误为-1000,或kCFStreamErrorHTTPAuthenticationTypeUnsupported 从上的非常过时的源代码来看,这一切都可以正常工作。我已

收到带有“Proxy Authenticate:Basic realm=example.com”头的“407 Proxy authentication required”响应后,我将调用CFHTTPAuthenticationCreateFromResponse。这将返回无效的CFHTTPAuthenticationRef对象;错误为-1000,或kCFStreamErrorHTTPAuthenticationTypeUnsupported

从上的非常过时的源代码来看,这一切都可以正常工作。我已经在调试器中验证了一些内部结构,比如_方案,实际上被正确解析,因此我知道我的头值是正确的。很明显,CFHTTPAuthenticationCreateFromResponse中的代码已经更改,但是我不知道我需要做什么才能使它工作

从单步遍历汇编代码来看,这似乎与缺少URL有关。没有公共API向响应添加URL,事实上Basic和Digest auth不需要URL,这很奇怪

我在OSX Mavericks、iOS 7模拟器和iOS 8模拟器上观察到了这一点。我把它归结为一个简单的复制函数,粘贴在下面。我还尝试使用测试代理服务器和CFReadStream,从CFReadStreamCopyPropertyrequestStream、kCFStreamPropertyHTTPResponseHeader创建响应,但毫无效果,这可能会将URL与响应对象关联

void testCFAuthentication()
{
    Boolean result;
    CFStringRef str;
    const char *rawResponse = "HTTP/1.1 407 Proxy authentication required\r\nProxy-Authenticate: Basic realm=\"example.com\"\r\n\r\n";

    CFHTTPMessageRef responseMessage = NULL;
    responseMessage = CFHTTPMessageCreateEmpty(kCFAllocatorDefault, false);

    // Optional hack, doesn't help
    /*
    CFURLRef url = NULL;
    url = CFURLCreateWithString(NULL, CFSTR("https://example.com/"), NULL);
    _CFHTTPMessageSetResponseURL(responseMessage, url);
    NSLog(@"_CFHTTPMessageSetResponseURL called\n");
    */

    result = CFHTTPMessageAppendBytes(responseMessage, (uint8_t *)rawResponse, strlen(rawResponse));
    NSLog(@"CFHTTPMessageAppendBytes result: %d\n", (int)result);
    NSLog(@"CFHTTPMessageIsHeaderComplete: %d\n", (int)CFHTTPMessageIsHeaderComplete(responseMessage));
    NSLog(@"CFHTTPMessageGetResponseStatusCode: %d\n", (int)CFHTTPMessageGetResponseStatusCode(responseMessage));
    NSLog(@"CFHTTPMessageCopyResponseStatusLine: %s\n", CFStringGetCStringPtr(CFHTTPMessageCopyResponseStatusLine(responseMessage), kCFStringEncodingUTF8));
    NSLog(@"Proxy-Authenticate header value: %s\n", CFStringGetCStringPtr(CFHTTPMessageCopyHeaderFieldValue(responseMessage, CFSTR("Proxy-Authenticate")), kCFStringEncodingUTF8));

    CFHTTPAuthenticationRef auth = NULL;
    auth = CFHTTPAuthenticationCreateFromResponse(NULL, responseMessage);
    NSLog(@"CFHTTPAuthenticationCreateFromResponse:\n"); CFShow(auth);
    if (auth) {
        CFStreamError error = { 0 };
        result = CFHTTPAuthenticationIsValid(auth, &error);
        if (!result) {
            NSLog(@"CFHTTPAuthenticationIsValid: false, error %d (0x%x), domain %ld (0x%lx)\n", error.error, error.error, error.domain, error.domain);
        } else {
            NSLog(@"CFHTTPAuthenticationCopyMethod=%s\n", CFStringGetCStringPtr(CFHTTPAuthenticationCopyMethod(auth), kCFStringEncodingUTF8));
            NSLog(@"authRealm=%s\n", CFStringGetCStringPtr(CFHTTPAuthenticationCopyRealm(auth), kCFStringEncodingUTF8));
        }
    };
}
输出:

2015-02-13 11:01:05.654 CFHTTPMessageAppendBytes result: 1
2015-02-13 11:01:05.655 CFHTTPMessageIsHeaderComplete: 1
2015-02-13 11:01:05.656 CFHTTPMessageGetResponseStatusCode: 407
2015-02-13 11:01:05.657 CFHTTPMessageCopyResponseStatusLine: HTTP/1.1 407 Proxy authentication required
2015-02-13 11:01:05.657 Proxy-Authenticate header value: Basic realm="example.com"
2015-02-13 11:01:05.658 CFHTTPAuthenticationCreateFromResponse:
<CFHTTPAuthentication 0x7fe0d36017f0>{state = Failed; scheme = <undecided>, forProxy = true}
2015-02-13 11:01:05.658 CFHTTPAuthenticationIsValid: false, error -1000 (0xfffffc18), domain 4 (0x4)
你遇到了,但有点不同的味道。 问题是,CFHTTPAuthenticationCreateFromResponse仅适用于从CFHTTPStream获取的响应。 我找到了一个解决办法

公开私有API这将导致您无法通过Apple review

// exposing private API for workaround
extern void _CFHTTPMessageSetResponseURL(CFHTTPMessageRef, CFURLRef);
使用此专用API将URL添加到响应:

_CFHTTPMessageSetResponseURL(responseMessage, 
                             (__bridge CFURLRef)[NSURL URLWithString: "https://example.com/"]);
 auth = CFHTTPAuthenticationCreateFromResponse(NULL, responseMessage);