123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237 |
- /****************************************************************************
- Copyright (c) 2013-2017 Chukong Technologies Inc.
-
- http://www.cocos2d-x.org
-
- Permission is hereby granted, free of charge, to any person obtaining a copy
- of this software and associated documentation files (the "Software"), to deal
- in the Software without restriction, including without limitation the rights
- to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
- copies of the Software, and to permit persons to whom the Software is
- furnished to do so, subject to the following conditions:
-
- The above copyright notice and this permission notice shall be included in
- all copies or substantial portions of the Software.
-
- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
- OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
- THE SOFTWARE.
- ****************************************************************************/
- #include "platform/CCPlatformConfig.h"
- #if (CC_TARGET_PLATFORM == CC_PLATFORM_MAC) || (CC_TARGET_PLATFORM == CC_PLATFORM_IOS)
- #import "network/HttpAsynConnection-apple.h"
- @interface HttpAsynConnection ()
- @property (readwrite) NSString *statusString;
- @end
- @implementation HttpAsynConnection
- @synthesize srcURL = srcURL;
- @synthesize sslFile = sslFile;
- @synthesize responseHeader = responseHeader;
- @synthesize responseData = responseData;
- @synthesize getDataTime = getDataTime;
- @synthesize responseCode = responseCode;
- @synthesize statusString = statusString;
- @synthesize responseError = responseError;
- @synthesize connError = connError;
- @synthesize conn = conn;
- @synthesize finish = finish;
- @synthesize runLoop = runLoop;
- - (void)dealloc
- {
- [srcURL release];
- [sslFile release];
- [responseHeader release];
- [responseData release];
- [responseError release];
- [conn release];
- [runLoop release];
- [connError release];
-
- [super dealloc];
- }
- - (void) startRequest:(NSURLRequest *)request
- {
- #ifdef COCOS2D_DEBUG
- NSLog(@"Starting to load %@", srcURL);
- #endif
-
- finish = false;
- self.responseData = [NSMutableData data];
- getDataTime = 0;
- self.responseError = nil;
- self.connError = nil;
-
- // create the connection with the target request and this class as the delegate
- self.conn = [[[NSURLConnection alloc] initWithRequest:request
- delegate:self
- startImmediately:NO] autorelease];
-
- [self.conn scheduleInRunLoop:[NSRunLoop currentRunLoop] forMode:NSDefaultRunLoopMode];
-
- // start the connection
- [self.conn start];
- }
- #pragma mark NSURLConnectionDelegate methods
- /**
- * This delegate method is called when the NSURLConnection connects to the server. It contains the
- * NSURLResponse object with the headers returned by the server. This method may be called multiple times.
- * Therefore, it is important to reset the data on each call. Do not assume that it is the first call
- * of this method.
- **/
- - (void) connection:(NSURLConnection *)connection
- didReceiveResponse:(NSURLResponse *)response {
- #ifdef COCOS2D_DEBUG
- NSLog(@"Received response from request to url %@", srcURL);
- #endif
-
- NSHTTPURLResponse *httpResponse = (NSHTTPURLResponse *)response;
- //NSLog(@"All headers = %@", [httpResponse allHeaderFields]);
- self.responseHeader = [httpResponse allHeaderFields];
- responseCode = httpResponse.statusCode;
- self.statusString = [NSHTTPURLResponse localizedStringForStatusCode:responseCode];
- if(responseCode == 200)
- self.statusString = @"OK";
-
- /*The individual values of the numeric status codes defined for HTTP/1.1
- | "200" ; OK
- | "201" ; Created
- | "202" ; Accepted
- | "203" ; Non-Authoritative Information
- | "204" ; No Content
- | "205" ; Reset Content
- | "206" ; Partial Content
- */
- if (responseCode < 200 || responseCode >= 300)
- {// something went wrong, abort the whole thing
- self.responseError = [NSError errorWithDomain:@"CCBackendDomain"
- code:responseCode
- userInfo:@{NSLocalizedDescriptionKey: @"Bad HTTP Response Code"}];
- }
-
- [responseData setLength:0];
- }
- /**
- * This delegate method is called for each chunk of data received from the server. The chunk size
- * is dependent on the network type and the server configuration.
- */
- - (void)connection:(NSURLConnection *)connection
- didReceiveData:(NSData *)data
- {
- //NSLog(@"get some data");
- [responseData appendData:data];
- getDataTime++;
- }
- /**
- * This delegate method is called if the connection cannot be established to the server.
- * The error object will have a description of the error
- **/
- - (void)connection:(NSURLConnection *)connection
- didFailWithError:(NSError *)error
- {
- //NSLog(@"Load failed with error %@", [error localizedDescription]);
- self.connError = error;
-
- finish = true;
- }
- /**
- * This delegate method is called when the data load is complete. The delegate will be released
- * following this call
- **/
- - (void)connectionDidFinishLoading:(NSURLConnection *)connection
- {
- finish = true;
- }
- - (void)connection:(NSURLConnection *)connection didSendBodyData:(NSInteger)bytesWritten
- totalBytesWritten:(NSInteger)totalBytesWritten
- totalBytesExpectedToWrite:(NSInteger)totalBytesExpectedToWrite
- {
- NSLog(@"Received response from request to url didSendBodyData");
- }
- //Server evaluates client's certificate
- - (BOOL) shouldTrustProtectionSpace:(NSURLProtectionSpace*)protectionSpace
- {
- if(sslFile == nil)
- return YES;
- //load the bundle client certificate
- NSString *certPath = [[NSBundle mainBundle] pathForResource:sslFile ofType:@"der"];
- NSData *certData = [[NSData alloc] initWithContentsOfFile:certPath];
- CFDataRef certDataRef = (CFDataRef)certData;
- SecCertificateRef cert = SecCertificateCreateWithData(NULL, certDataRef);
-
- //Establish a chain of trust anchored on our bundled certificate
- CFArrayRef certArrayRef = CFArrayCreate(NULL, (void*)&cert, 1, NULL);
- SecTrustRef serverTrust = protectionSpace.serverTrust;
- SecTrustSetAnchorCertificates(serverTrust, certArrayRef);
-
- //Verify that trust
- SecTrustResultType trustResult;
- SecTrustEvaluate(serverTrust, &trustResult);
-
- if(trustResult == kSecTrustResultRecoverableTrustFailure)
- {
- CFDataRef errDataRef = SecTrustCopyExceptions(serverTrust);
- SecTrustSetExceptions(serverTrust, errDataRef);
- SecTrustEvaluate(serverTrust, &trustResult);
- CFRelease(errDataRef);
- }
- [certData release];
- if (cert)
- {
- CFRelease(cert);
- }
- if (certArrayRef)
- {
- CFRelease(certArrayRef);
- }
- //Did our custom trust chain evaluate successfully?
- return trustResult == kSecTrustResultUnspecified || trustResult == kSecTrustResultProceed;
- }
- - (void) connection:(NSURLConnection *)connection willSendRequestForAuthenticationChallenge:(NSURLAuthenticationChallenge *)challenge
- {
- id <NSURLAuthenticationChallengeSender> sender = challenge.sender;
- NSURLProtectionSpace *protectionSpace = challenge.protectionSpace;
-
- //Should server trust client?
- if([self shouldTrustProtectionSpace:protectionSpace])
- {
- SecTrustRef trust = [protectionSpace serverTrust];
- //
- // SecCertificateRef certificate = SecTrustGetCertificateAtIndex(trust, 0);
- //
- // NSData *serverCertificateData = (NSData*)SecCertificateCopyData(certificate);
- // NSString *serverCertificateDataHash = [[serverCertificateData base64EncodedString] ]
- NSURLCredential *credential = [NSURLCredential credentialForTrust:trust];
- [sender useCredential:credential forAuthenticationChallenge:challenge];
- }
- else
- {
- [sender cancelAuthenticationChallenge:challenge];
- }
- }
- @end
- #endif // #if (CC_TARGET_PLATFORM == CC_PLATFORM_MAC) || (CC_TARGET_PLATFORM == CC_PLATFORM_IOS)
|