root / Assets / Plugins / UnityHTTP / DiskCache.cs @ 9:37719e88568d
History | View | Annotate | Download (3.6 kB)
1 | using UnityEngine; |
---|---|
2 | using System.Collections; |
3 | using System.IO; |
4 | using System; |
5 | using HTTP; |
6 | |
7 | namespace HTTP |
8 | { |
9 | public class DiskCacheOperation |
10 | { |
11 | public bool isDone = false; |
12 | public bool fromCache = false; |
13 | public Request request = null; |
14 | } |
15 | |
16 | #if UNITY_WEBPLAYER |
17 | public class DiskCache : MonoBehaviour |
18 | { |
19 | static DiskCache _instance = null; |
20 | public static DiskCache Instance { |
21 | get { |
22 | if (_instance == null) { |
23 | var g = new GameObject ("DiskCache", typeof(DiskCache)); |
24 | g.hideFlags = HideFlags.HideAndDontSave; |
25 | _instance = g.GetComponent<DiskCache> (); |
26 | } |
27 | return _instance; |
28 | } |
29 | } |
30 | |
31 | public DiskCacheOperation Fetch (Request request) |
32 | { |
33 | var handle = new DiskCacheOperation (); |
34 | handle.request = request; |
35 | StartCoroutine (Download (request, handle)); |
36 | return handle; |
37 | } |
38 | |
39 | IEnumerator Download(Request request, DiskCacheOperation handle) |
40 | { |
41 | request.Send (); |
42 | while (!request.isDone) |
43 | yield return new WaitForEndOfFrame (); |
44 | handle.isDone = true; |
45 | } |
46 | } |
47 | #else |
48 | public class DiskCache : MonoBehaviour |
49 | { |
50 | string cachePath = null; |
51 | |
52 | static DiskCache _instance = null; |
53 | public static DiskCache Instance { |
54 | get { |
55 | if (_instance == null) { |
56 | var g = new GameObject ("DiskCache", typeof(DiskCache)); |
57 | g.hideFlags = HideFlags.HideAndDontSave; |
58 | _instance = g.GetComponent<DiskCache> (); |
59 | } |
60 | return _instance; |
61 | } |
62 | } |
63 | |
64 | void Awake () |
65 | { |
66 | cachePath = System.IO.Path.Combine (Environment.GetFolderPath (Environment.SpecialFolder.LocalApplicationData), "uwcache"); |
67 | if (!Directory.Exists (cachePath)) |
68 | Directory.CreateDirectory (cachePath); |
69 | } |
70 | |
71 | public DiskCacheOperation Fetch (Request request) |
72 | { |
73 | var guid = ""; |
74 | // MD5 is disposable |
75 | // http://msdn.microsoft.com/en-us/library/system.security.cryptography.md5.aspx#3 |
76 | using (System.Security.Cryptography.MD5 md5 = System.Security.Cryptography.MD5.Create ()) { |
77 | foreach (var b in md5.ComputeHash (System.Text.ASCIIEncoding.ASCII.GetBytes (request.uri.ToString ()))) { |
78 | guid = guid + b.ToString ("X2"); |
79 | } |
80 | } |
81 | |
82 | var filename = System.IO.Path.Combine (cachePath, guid); |
83 | if (File.Exists (filename) && File.Exists (filename + ".etag")) |
84 | request.SetHeader ("If-None-Match", File.ReadAllText (filename + ".etag")); |
85 | var handle = new DiskCacheOperation (); |
86 | handle.request = request; |
87 | StartCoroutine (DownloadAndSave (request, filename, handle)); |
88 | return handle; |
89 | } |
90 | |
91 | IEnumerator DownloadAndSave (Request request, string filename, DiskCacheOperation handle) |
92 | { |
93 | var useCachedVersion = File.Exists(filename); |
94 | Action< HTTP.Request > callback = request.completedCallback; |
95 | request.Send(); // will clear the completedCallback |
96 | while (!request.isDone) |
97 | yield return new WaitForEndOfFrame (); |
98 | if (request.exception == null && request.response != null) { |
99 | if (request.response.status == 200) { |
100 | var etag = request.response.GetHeader ("etag"); |
101 | if (etag != "") { |
102 | File.WriteAllBytes (filename, request.response.bytes); |
103 | File.WriteAllText (filename + ".etag", etag); |
104 | } |
105 | useCachedVersion = false; |
106 | } |
107 | } |
108 | |
109 | if(useCachedVersion) { |
110 | if(request.exception != null) { |
111 | Debug.LogWarning("Using cached version due to exception:" + request.exception); |
112 | request.exception = null; |
113 | } |
114 | request.response.status = 304; |
115 | request.response.bytes = File.ReadAllBytes (filename); |
116 | request.isDone = true; |
117 | } |
118 | handle.isDone = true; |
119 | |
120 | if ( callback != null ) |
121 | { |
122 | callback( request ); |
123 | } |
124 | } |
125 | |
126 | } |
127 | #endif |
128 | } |