Ben Copsey

Added automatic redirection for 30x headers (on by default)

... ... @@ -214,6 +214,9 @@ extern NSString* const NetworkRequestErrorDomain;
// Use HTTP 1.0 rather than 1.1 (defaults to false)
BOOL useHTTPVersionOne;
// When YES, requests will automatically redirect when they get a HTTP 30x header (defaults to YES)
BOOL shouldRedirect;
}
... ... @@ -397,5 +400,5 @@ extern NSString* const NetworkRequestErrorDomain;
@property (assign) BOOL didCreateTemporaryPostDataFile;
@property (assign) BOOL useHTTPVersionOne;
@property (assign, readonly) unsigned long long partialDownloadSize;
@property (assign) BOOL shouldRedirect;
@end
... ...
... ... @@ -88,6 +88,7 @@ static NSError *ASIUnableToCreateRequestError;
self = [super init];
[self setRequestMethod:@"GET"];
[self setShouldRedirect:YES];
[self setShowAccurateProgress:YES];
[self setShouldResetProgressIndicators:YES];
[self setAllowCompressedResponse:YES];
... ... @@ -305,12 +306,13 @@ static NSError *ASIUnableToCreateRequestError;
}
// Create a new HTTP request.
request = CFHTTPMessageCreateRequest(kCFAllocatorDefault, (CFStringRef)requestMethod, (CFURLRef)url, self.useHTTPVersionOne ? kCFHTTPVersion1_0 : kCFHTTPVersion1_1);
request = CFHTTPMessageCreateRequest(kCFAllocatorDefault, (CFStringRef)requestMethod, (CFURLRef)url, [self useHTTPVersionOne] ? kCFHTTPVersion1_0 : kCFHTTPVersion1_1);
if (!request) {
[self failWithError:ASIUnableToCreateRequestError];
return;
}
// If we've already talked to this server and have valid credentials, let's apply them to the request
if (useSessionPersistance && sessionCredentials && sessionAuthentication) {
if (!CFHTTPMessageApplyCredentialDictionary(request, sessionAuthentication, (CFMutableDictionaryRef)sessionCredentials, NULL)) {
... ... @@ -428,6 +430,9 @@ static NSError *ASIUnableToCreateRequestError;
[self failWithError:[NSError errorWithDomain:NetworkRequestErrorDomain code:ASIInternalErrorWhileBuildingRequestType userInfo:[NSDictionary dictionaryWithObjectsAndKeys:@"Unable to create read stream",NSLocalizedDescriptionKey,nil]]];
return;
}
// Tell CFNetwork to automatically redirect for 30x status codes
CFReadStreamSetProperty(readStream, kCFStreamPropertyHTTPShouldAutoredirect, [self shouldRedirect] ? kCFBooleanTrue : kCFBooleanFalse);
// Set the client
CFStreamClientContext ctxt = {0, self, NULL, NULL, NULL};
... ... @@ -1634,4 +1639,5 @@ static NSError *ASIUnableToCreateRequestError;
@synthesize fileDownloadOutputStream;
@synthesize authenticationRetryCount;
@synthesize updatedProgress;
@synthesize shouldRedirect;
@end
... ...
... ... @@ -126,10 +126,39 @@
GHAssertTrue(success,@"Wrong HTTP version used");
}
- (void)testAutomaticRedirection
{
ASIHTTPRequest *request;
BOOL success;
int i;
for (i=301; i<308; i++) {
NSURL *url = [NSURL URLWithString:[NSString stringWithFormat:@"http://allseeing-i.com/ASIHTTPRequest/tests/redirect/%hi",i]];
request = [ASIHTTPRequest requestWithURL:url];
[request setShouldRedirect:NO];
[request start];
NSLog([request responseString]);
if (i == 304) { // 304s will not contain a body, as per rfc2616. Will test 304 handling in a future test when we have etag support
continue;
}
success = [[request responseString] isEqualToString:[NSString stringWithFormat:@"Non-redirected content with %hi status code",i]];
GHAssertTrue(success,[NSString stringWithFormat:@"Got the wrong content when not redirecting after a %hi",i]);
request = [ASIHTTPRequest requestWithURL:url];
[request start];
NSLog([request responseString]);
success = [[request responseString] isEqualToString:[NSString stringWithFormat:@"Redirected content after a %hi status code",i]];
GHAssertTrue(success,[NSString stringWithFormat:@"Got the wrong content when redirecting after a %hi",i]);
success = ([request responseStatusCode] == 200);
GHAssertTrue(success,[NSString stringWithFormat:@"Got the wrong status code (expected %hi)",i]);
}
}
- (void)testUploadContentLength
{
//This url will return the contents of the Content-Length request header
NSURL *url = [[[NSURL alloc] initWithString:@"http://allseeing-i.com/ASIHTTPRequest/tests/content-length"] autorelease];
NSURL *url = [NSURL URLWithString:@"http://allseeing-i.com/ASIHTTPRequest/tests/content-length"];
ASIHTTPRequest *request = [[[ASIHTTPRequest alloc] initWithURL:url] autorelease];
[request setPostBody:[NSMutableData dataWithLength:1024*32]];
[request start];
... ...