Tôi có UIWebview giúp thực hiện cuộc gọi AJAX đến các dịch vụ bên ngoài. Khi offline tôi cần nắm bắt các yêu cầu và trả về json cục bộ.Làm thế nào để thử gọi AJAX với NSURLProtocol?
Tôi thực hiện một NSURLProtocol và tôi quản lý để nắm bắt những yêu cầu AJAX, vấn đề được jquery luôn trả về một mã 0 lỗi:
$.ajax({
url: url,
dataType: 'json',
contentType: "application/json",
success: function(jsonData){
alert("success :");
},
error: function (request, status, error) {
alert("failure :" + request.status);
}
});
tôi luôn có được một request.status = 0
Để kiểm tra giao thức của tôi, tôi đã cố gắng để thử một hình ảnh bên html của tôi và nó hoạt động tuyệt vời.
- yêu cầu HTML để một hình ảnh từ google.fr =>hoạt động tốt
- gọi AJAX đến một json trên amazon =>không
Đây là thực hiện đầy đủ của tôi:
#import "EpubProtocol.h"
@implementation EpubProtocol
#pragma mark - NSURLProtocol
+ (BOOL)canInitWithRequest:(NSURLRequest *)request {
BOOL awsRequest = [self request:request contains:@"s3.amazonaws.com"];
BOOL imgRequest = [self request:request contains:@"google.fr"];
BOOL match = awsRequest || imgRequest;
return match;
}
+ (NSURLRequest*)canonicalRequestForRequest:(NSURLRequest*)theRequest
{
return theRequest;
}
- (void)startLoading {
NSURLRequest *request = [self request];
//Mock Amazon call
if([EpubProtocol request:request contains:@"s3.amazonaws.com"]) {
NSString *path = [[NSBundle bundleForClass:self.class] pathForResource:@"epub1" ofType:@"json"];
NSData *data = [NSData dataWithContentsOfFile:path];
[self mockRequest:request mimeType:@"application/json" data:data];
}
//Mock image call
else if([EpubProtocol request:request contains:@"google.fr"]) {
NSOperationQueue *queue = [[NSOperationQueue alloc] init];
[NSURLConnection sendAsynchronousRequest:[NSURLRequest requestWithURL:[NSURL URLWithString:@"http://www.itespresso.fr/wp-content/gallery/yahoo/1-yahoo-logo.jpg"]] queue:queue completionHandler:^(NSURLResponse *response, NSData *data, NSError *error) {
[self mockRequest:request mimeType:@"image/jpeg" data:data];
}];
}
}
- (void)stopLoading
{
NSLog(@"Did stop loading");
}
#pragma mark - Request utils
+ (BOOL) request:(NSURLRequest*)request contains:(NSString*)domain {
NSString *str = [[request URL] absoluteString];
NSPredicate *pred = [NSPredicate predicateWithFormat:@"SELF contains[cd] %@", domain];
return [pred evaluateWithObject:str];
}
#pragma mark - Mock responses
-(void) mockRequest:(NSURLRequest*)request mimeType:(NSString*)mimeType data:(NSData*)data {
id client = [self client];
NSHTTPURLResponse *response = [[NSHTTPURLResponse alloc] initWithURL:[request URL] MIMEType:mimeType expectedContentLength:-1 textEncodingName:nil];
[client URLProtocol:self didReceiveResponse:response
cacheStoragePolicy:NSURLCacheStorageNotAllowed];
[client URLProtocol:self didLoadData:data];
[client URLProtocolDidFinishLoading:self];
}
@end
Công việc tuyệt vời. Câu trả lời rất hữu ích! –
Điều này đã cứu ngày của tôi. BTW cho mọi người tự hỏi, vì bạn không thể gọi cả hai initializers (mimeType một, so với tiêu đề/statusCode một) bạn CÓ THỂ thiết lập mimeType, mã hóa, chiều dài, vv bằng cách sử dụng tiêu đề HTTP tiêu chuẩn: https://en.wikipedia.org/wiki/List_of_HTTP_header_fields. Chỉ cần thêm vào từ điển đầu trang của bạn –