UIWebView не всегда вызывает - [NSURLCache storeCachedResponse: forRequest:] - PullRequest
9 голосов
/ 27 января 2012

Кажется, что UIWebView не всегда вызывает storeCachedResponse:forRequest: при загрузке ресурса.Кто-нибудь знает почему?Я пытаюсь кешировать изображения с помощью -[NSURLCache storeCachedResponse:forRequest:], большую часть работы он выполняет нормально, однако в некоторых случаях UIWebView не вызывает этот метод при загрузке страницы, где на самом деле есть изображения.

Ответы [ 5 ]

11 голосов
/ 02 апреля 2012

Ответ на запрос провайдера:

Я вижу это и для маленьких файлов (100 байт). Веб-просмотр также не может позвонить cachedResponseForRequest:

Я нашел этот вопрос , который напрямую обращается к этому поведению:

Несмотря на документацию Apple с указанием в противном случае , NSURLCache на iOS вообще не выполняет никакого кэширования диска (флэш). You может подкласс NSURLCache изменить поведение выборки и хранить операции для использования диска (например, SDURLCache делает), но из-за следуя строгим ограничениям того, как кэш используется и реализован, это не работает так, как вы ожидаете:

  • NSURLConnection даже не вызывает storeCachedResponse:forRequest: для файлов размером более 50 КБ (> = 52428 байты, если быть точным). Это делает подклассы NSURLCache бессмысленными для наше использование (изображения 200 КБ), потому что оно даже не попадет в кеш. Как результат, мы должны добавить кеширование вручную на уровне выше NSURLConnection.

  • Даже когда кто-либо вызывает встроенный NSURLCache storeCachedResponse:forRequest: вручную, он сохраняет только ответ в памяти, если он меньше, чем около 180 КБ. Я проверил это вызываем storeCachedResponse вручную и видим, что до / после currentMemoryUsage не изменилось при длине данных выше 180 КБ. Поэтому мы должны написать и собственное кэширование памяти LRU.

(Акцент мой.)

Кажется, это ответственно за вызываемое поведение. Поскольку текущий принятый ответ указывает , ASIHTTPRequest - ожидаемый обходной путь для этого поведения.

Однако обратите внимание на предостережение в верхней части страницы:

Обратите внимание, что я больше не работаю над этой библиотекой - возможно, вы захотите использовать что-то еще для новых проектов. :)

Вам следует подумать о том, чтобы полагаться на поддерживаемые библиотеки или, если вы предпочитаете, внести свой вклад в эту библиотеку, если она лежит в основе вашего кода.

4 голосов
/ 28 марта 2012

Как описано здесь NSURLConnection не вызывает storeCachedResponse:forRequest:, если размер файла превышает 50 КБ (52428 байт).
Попробуйте ASIHTTPRequest кеширование .

3 голосов
/ 28 ноября 2014

NSURLCache работает с двумя разными кешами: кеш на диске и кеш в памяти

  • Ответы будут кэшироваться в кэш-памяти в памяти, если размер ответа меньше 50kb и
  • Ответы будут кэшироваться в кэш на диске, если размер ответа превышает 50kb

Если вы инициализируете NSURLCache с diskPath nil, то кэш на диске не будет активным, и storeCachedResponse:forRequest: будет вызываться только для ответов размером менее 50 КБ.

Так что настройте URLCache следующим образом

[[MYCustomURLCache alloc] initWithMemoryCapacity:4 * 1024 * 1024 
                          diskCapacity:20 * 1024 * 1024 
                          diskPath:@"urlcache.db"];
2 голосов
/ 25 января 2013

Я не уверен, как это работает для UIWebvieuw, но когда вы используете NSURLRequest, максимальный размер файла зависит от того, как вы инициализируете URLCache (initWithMemoryCapacity: (NSUInteger) memoryCapacity ...) Я просто кэшировал 2 МБфайл

2 голосов
/ 30 марта 2012

Вы проверили статус HTTP и заголовки кэша?Истекает, Cache-Control и т. Д.?Может сервер отвечает со статусом = 304 без тела ответа?

- (void)connection:(NSURLConnection *)conn didReceiveResponse:(NSURLResponse *)aResponse 
{
  NSLog(@"CODE: %d", ((NSHTTPURLResponse *)aResponse).statusCode);
  NSLog(@"HEADERS: %@", ((NSHTTPURLResponse *)aResponse).allHeaderFields);
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...