iOSのWebviewのキャッシュはどこにいくのだろう

July 7, 2014

この記事はQiitaの記事をエクスポートしたものです。内容が古くなっている可能性があります。

検証端末

  • iOS 7
  • iPhone 4S

Cache.dbの中をみる

WebviewのディスクキャッシュはどうやらCache.dbというファイルに記録されている模様である.そこでiFuxBoxで取り出してみて解析してみた.

iFunBoxで該当アプリ以下のLibrary/CachesをMac上に取り出す. Caches/バンドルID/Cache.dbにsqliteのDBファイルがあるので,sqliteで開く.

% sqlite3 Cache.db

とりあえず,テーブル一覧を見てみる.

sqlite> .tables
cfurl_cache_blob_data       cfurl_cache_response
cfurl_cache_receiver_data   cfurl_cache_schema_version

次はスキーマを見てみる.

sqlite> .schema cfurl_cache_response
CREATE TABLE cfurl_cache_response(entry_ID INTEGER PRIMARY KEY
AUTOINCREMENT UNIQUE,                                     version
INTEGER, hash_value INTEGER, storage_policy INTEGER, request_key TEXT
UNIQUE,                                     time_stamp NOT NULL
DEFAULT CURRENT_TIMESTAMP, partition TEXT);
CREATE INDEX request_key_index ON cfurl_cache_response(request_key);
CREATE INDEX time_stamp_index ON cfurl_cache_response(time_stamp);

ほうほう.

他のテーブルのスキーマを調べたところ,こんな感じになっていた. 一部,勘だったり,わからないところもあった.

cfurl_cache_responseテーブル

  • entry_ID: キャッシュのID
  • version: わからない(キャッシュのバージョン?)
  • hash_value: たぶん,レスポンスのハッシュ値
  • storage_policy: わからない
  • request_key: リクエストのURL
  • time_stamp: タイムスタンプ
  • partition: わからない

cfurl_cache_blob_dataテーブル

  • entry_ID: キャッシュのID
  • response_object: レスポンスヘッダ?(BLOB),plist形式
  • request_object: リクエストヘッダ?(BLOB), plist形式
  • user_info: わからない

cfurl_cache_receiver_dataテーブル

  • entry_ID: キャッシュのID
  • isDataOnFS: 1:ファイルとして保存,0: receiver_dataに保存
  • receiver_data: isDataOnFS が0の場合は受け取ったデータのBLOB, 1の場合はファイルとして保存されている場合のファイル名(Library/Caches/バンドルID/fsCachedData以下にある)

キャッシュされたファイルを取り出す

上記のようなスキーマになっているので,ファイルを取り出すのは簡単だ.

まずはcfurl_cache_responseテーブルから,それっぽいURLを検索して,entry_IDを絞る. 今回は1x50.pngという画像を検索してみた.

sqlite> select * from cfurl_cache_response where request_key like '%/1x50.png';
108|0|3915446248|0|http://xxxxx/img/1x50.png|2014-07-06 14:24:26|

entry_ID108なので,cfurl_cache_receiver_dataを検索してみる.

sqlite> select entry_ID, isDataOnFS, hex(receiver_data) from cfurl_cache_receiver_data where entry_ID=108;
108|0|89504E470D0A1A0A0000000D4948445200000001000000320802000000129926DD0000001649444154789C626A68686062606018EA18100000FFFF51AF01E5F024F2350000000049454E44AE426082

このファイルは小さいので,ファイルとして書き出されずに直接DBに突っ込まれている.BLOBのまま出力しても化けるだけなので,hexで16進で表示させている.

ちなみに,isDataOnFSが1の時は,Library/Caches/バンドルID/fsCachedData以下に,ファイルとして保存される.そして,ファイル名はreceiver_dataに入っている.

sqlite> select * from cfurl_cache_receiver_data where isDataOnFS=1 limit 1;
140|1|327B2D66-B3E5-428D-B3EB-30FFA815875B

この場合は327B2D66-B3E5-428D-B3EB-30FFA815875Bという名前で保存されている.

% file fsCachedData/327B2D66-B3E5-428D-B3EB-30FFA815875B
fsCachedData/327B2D66-B3E5-428D-B3EB-30FFA815875B: PNG image data, 1634 x 2224, 8-bit/color RGBA, non-interlaced

ちなみに,保存されていたのは,この画像.でかい.

327B2D66-B3E5-428D-B3EB-30FFA815875B.png