可变的NSHTTPURLResponse或NSURLResponse

时间:2010-01-19 20:01:03

标签: nsurlconnection iphone nsurlrequest nsurlcache

我需要修改NSURLResponse中的响应头。这可能吗?

4 个答案:

答案 0 :(得分:9)

我刚和朋友谈论这件事。我的建议是写一个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并将其全部放在一个类别中。

答案 1 :(得分:3)

您可以使用allHeaderFields方法将它们读入NSDictionary。

    NSHTTPURLResponse *httpResponse = (NSHTTPURLResponse *)response;
    NSDictionary *httpResponseHeaderFields = [httpResponse
allHeaderFields];

为了100%安全,你想用

包装它
if ([response respondsToSelector:@selector(allHeaderFields)]) {... }

答案 2 :(得分:1)

我有类似的问题。我想修改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中

答案 3 :(得分:-1)

你可以这样做,而且你需要NSHTTPURLResponse而不是NSURLResponse,因为在Swift中,NSURLResponse可以与许多协议一起使用,而不仅仅是http,例如ftpdata: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()