【发布时间】:2010-01-19 20:01:02
【问题描述】:
我需要修改 NSURLResponse 中的响应标头。这可能吗?
【问题讨论】:
-
您是否尝试修改从服务器获取的标头?!你是说 NSURLRequest 吗?
-
等等……不……我的意思是 NSURLResponse
标签: nsurlconnection iphone nsurlrequest nsurlcache
我需要修改 NSURLResponse 中的响应标头。这可能吗?
【问题讨论】:
标签: nsurlconnection iphone nsurlrequest nsurlcache
我刚刚和一个朋友谈论这个。我的建议是写一个 NSURLResponse 的子类。大致如下:
@interface MyHTTPURLResponse : NSURLResponse { NSDictionary *myDict; }
- (void)setAllHeaderFields:(NSDictionary *)dictionary;
@end
@implementation MyHTTPURLResponse
- (NSDictionary *)allHeaderFields { return myDict ?: [super allHeaderFields]; }
- (void)setAllHeaderFields:(NSDictionary *)dict { if (myDict != dict) { [myDict release]; myDict = [dict retain]; } }
@end
如果您正在处理不是您制作的对象,您可以尝试使用object_setClass 来调出课程。但是我不知道这是否会添加必要的实例变量。如果您可以支持足够新的 SDK,您也可以使用 objc_setAssociatedObject 并将其全部放入一个类别中。
【讨论】:
您可以使用allHeaderFields 方法将它们读入NSDictionary。
NSHTTPURLResponse *httpResponse = (NSHTTPURLResponse *)response;
NSDictionary *httpResponseHeaderFields = [httpResponse
allHeaderFields];
为了 100% 安全,您需要将其包裹起来
if ([response respondsToSelector:@selector(allHeaderFields)]) {... }
【讨论】:
我遇到了类似的问题。我想修改 http url 响应的头文件。我需要它是因为想向 UIWebView 提供缓存的 url 响应,并想欺骗 Web 视图,使响应没有过期(即我想更改标头的“Cache-Control”属性但保留其余的标头)。我的解决方案是使用 NSKeyedArchiver 对原始 http 响应进行编码,并使用委托拦截序列化。在
-(id) archiver:(NSKeyedArchiver*) archiver willEncodeObject:(id) object
我检查对象是否为 NSDictionary,如果是,我返回修改后的字典(即更新的“Cache-Control”标头)。之后我只是使用 NSKeyedUnarchiver 反序列化了序列化的响应。当然,您可以连接到 unarchiver 并修改其委托中的标头。
请注意,在 iOS 5 中 Apple 已添加
-(id)initWithURL:(NSURL*) url statusCode:(NSInteger) statusCode HTTPVersion:(NSString*) HTTPVersion headerFields:(NSDictionary*) headerFields
不在文档中(文档错误),但在 NSHTTPURLResponse 的公共 API 中
【讨论】:
你可以这样做,你需要NSHTTPURLResponse 而不是NSURLResponse,因为在 Swift 中,NSURLResponse 可以与许多协议一起使用,而不仅仅是http,例如ftp、@987654326 @,或https。因此,您可以调用它来获取元数据信息,例如预期的内容类型、mime 类型和文本编码,而NSHTTURLResponse 负责处理 HTTP 协议响应。因此,它是操纵标题的人。
这是一个小代码,它从响应中操作标题键 Server,并打印更改前后的值。
let url = "https://www.google.com"
let request = NSMutableURLRequest(URL: NSURL(string: url)!)
let session = NSURLSession.sharedSession()
let task = session.dataTaskWithRequest(request, completionHandler: {(data, response, error) in
if let response = response {
let nsHTTPURLResponse = response as! NSHTTPURLResponse
var headers = nsHTTPURLResponse.allHeaderFields
print ("The value of the Server header before is: \(headers["Server"]!)")
headers["Server"] = "whatever goes here"
print ("The value of the Server header after is: \(headers["Server"]!)")
}
})
task.resume()
【讨论】: