OLD | NEW |
---|---|
(Empty) | |
1 // Copyright (c) 2014 The Chromium Authors. All rights reserved. | |
2 // Use of this source code is governed by a BSD-style license that can be | |
3 // found in the LICENSE file. | |
4 | |
5 #include <set> | |
6 | |
7 #include "base/test/test_simple_task_runner.h" | |
8 #include "content/browser/indexed_db/indexed_db_active_blob_registry.h" | |
9 #include "content/browser/indexed_db/indexed_db_backing_store.h" | |
10 #include "content/browser/indexed_db/indexed_db_factory.h" | |
11 #include "content/browser/indexed_db/indexed_db_fake_backing_store.h" | |
12 #include "testing/gtest/include/gtest/gtest.h" | |
13 | |
14 namespace content { | |
15 | |
16 namespace { | |
17 | |
18 class MockIDBFactory : public IndexedDBFactory { | |
19 public: | |
20 MockIDBFactory() : IndexedDBFactory(NULL), duplicate_calls_(false) {} | |
21 | |
22 virtual void ReportOutstandingBlobs(const GURL& origin_url, | |
23 bool blobs_outstanding) OVERRIDE { | |
24 if (blobs_outstanding) { | |
25 if (origins_.count(origin_url)) { | |
26 duplicate_calls_ = true; | |
27 } else { | |
28 origins_.insert(origin_url); | |
29 } | |
30 } else { | |
31 if (!origins_.count(origin_url)) { | |
32 duplicate_calls_ = true; | |
33 } else { | |
34 origins_.erase(origin_url); | |
35 } | |
36 } | |
37 } | |
38 | |
39 bool CheckNoOriginsInUse() const { | |
40 return !duplicate_calls_ && !origins_.size(); | |
41 } | |
42 bool CheckSingleOriginInUse(const GURL& origin) const { | |
43 return !duplicate_calls_ && origins_.size() == 1 && origins_.count(origin); | |
44 } | |
45 | |
46 protected: | |
47 virtual ~MockIDBFactory() {} | |
48 | |
49 private: | |
50 std::set<GURL> origins_; | |
51 bool duplicate_calls_; | |
52 }; | |
53 | |
54 class MockIDBBackingStore : public IndexedDBFakeBackingStore { | |
55 public: | |
56 MockIDBBackingStore(IndexedDBFactory* factory, base::TaskRunner* task_runner) | |
57 : IndexedDBFakeBackingStore(factory, task_runner), | |
58 duplicate_calls_(false) {} | |
59 | |
60 virtual void ReportBlobUnused(int64 database_id, int64 blob_key) OVERRIDE { | |
61 unused_blobs_.insert(std::make_pair(database_id, blob_key)); | |
62 } | |
63 | |
64 typedef std::pair<int64, int64> KeyPair; | |
65 typedef std::set<KeyPair> KeyPairSet; | |
66 bool CheckUnusedBlobsEmpty() const { | |
67 return !duplicate_calls_ && !unused_blobs_.size(); | |
68 } | |
69 bool CheckSingleUnusedBlob(int64 database_id, int64 blob_key) const { | |
70 return !duplicate_calls_ && unused_blobs_.size() == 1 && | |
71 unused_blobs_.count(std::make_pair(database_id, blob_key)); | |
72 } | |
73 | |
74 const KeyPairSet& unused_blobs() const { return unused_blobs_; } | |
75 | |
76 protected: | |
77 virtual ~MockIDBBackingStore() {} | |
78 | |
79 private: | |
80 KeyPairSet unused_blobs_; | |
81 bool duplicate_calls_; | |
82 }; | |
83 | |
84 // Base class for our test fixtures. | |
85 class IndexedDBActiveBlobRegistryTest : public testing::Test { | |
86 public: | |
87 IndexedDBActiveBlobRegistryTest() | |
88 : task_runner_(new base::TestSimpleTaskRunner), | |
89 factory_(new MockIDBFactory), | |
90 backing_store_(new MockIDBBackingStore(factory_, task_runner_)), | |
91 registry_(new IndexedDBActiveBlobRegistry(backing_store_.get())) {} | |
92 | |
93 void RunUntilIdle() { task_runner_->RunUntilIdle(); } | |
94 MockIDBFactory* factory() const { return factory_.get(); } | |
95 MockIDBBackingStore* backing_store() const { return backing_store_.get(); } | |
96 IndexedDBActiveBlobRegistry* registry() const { return registry_.get(); } | |
97 | |
98 static const int64 DATABASE_ID_0 = 7; | |
jsbell
2014/03/20 18:04:33
Naming style is kDatabaseId0
ericu
2014/03/25 01:22:14
Done.
| |
99 static const int64 DATABASE_ID_1 = 12; | |
100 static const int64 BLOB_KEY_0 = 77; | |
101 static const int64 BLOB_KEY_1 = 14; | |
102 | |
103 typedef webkit_blob::ShareableFileReference::FinalReleaseCallback | |
104 ReleaseCallback; | |
105 | |
106 private: | |
107 scoped_refptr<base::TestSimpleTaskRunner> task_runner_; | |
108 scoped_refptr<MockIDBFactory> factory_; | |
109 scoped_refptr<MockIDBBackingStore> backing_store_; | |
110 scoped_ptr<IndexedDBActiveBlobRegistry> registry_; | |
111 | |
112 DISALLOW_COPY_AND_ASSIGN(IndexedDBActiveBlobRegistryTest); | |
113 }; | |
114 | |
115 TEST_F(IndexedDBActiveBlobRegistryTest, DeleteUnused) { | |
116 EXPECT_TRUE(factory()->CheckNoOriginsInUse()); | |
117 EXPECT_TRUE(backing_store()->CheckUnusedBlobsEmpty()); | |
118 | |
119 EXPECT_FALSE(registry()->MarkDeletedCheckIfUsed(DATABASE_ID_0, BLOB_KEY_0)); | |
120 RunUntilIdle(); | |
121 | |
122 EXPECT_TRUE(factory()->CheckNoOriginsInUse()); | |
123 EXPECT_TRUE(backing_store()->CheckUnusedBlobsEmpty()); | |
124 } | |
125 | |
126 TEST_F(IndexedDBActiveBlobRegistryTest, SimpleUse) { | |
127 EXPECT_TRUE(factory()->CheckNoOriginsInUse()); | |
128 EXPECT_TRUE(backing_store()->CheckUnusedBlobsEmpty()); | |
129 | |
130 base::Closure add_ref = | |
131 registry()->GetAddBlobRefCallback(DATABASE_ID_0, BLOB_KEY_0); | |
132 ReleaseCallback release = | |
133 registry()->GetFinalReleaseCallback(DATABASE_ID_0, BLOB_KEY_0); | |
134 add_ref.Run(); | |
135 RunUntilIdle(); | |
136 | |
137 EXPECT_TRUE(factory()->CheckSingleOriginInUse(backing_store()->origin_url())); | |
138 EXPECT_TRUE(backing_store()->CheckUnusedBlobsEmpty()); | |
139 | |
140 release.Run(base::FilePath()); | |
141 RunUntilIdle(); | |
142 | |
143 EXPECT_TRUE(factory()->CheckNoOriginsInUse()); | |
144 EXPECT_TRUE(backing_store()->CheckUnusedBlobsEmpty()); | |
145 } | |
146 | |
147 TEST_F(IndexedDBActiveBlobRegistryTest, DeleteWhileInUse) { | |
148 EXPECT_TRUE(factory()->CheckNoOriginsInUse()); | |
149 EXPECT_TRUE(backing_store()->CheckUnusedBlobsEmpty()); | |
150 | |
151 base::Closure add_ref = | |
152 registry()->GetAddBlobRefCallback(DATABASE_ID_0, BLOB_KEY_0); | |
153 ReleaseCallback release = | |
154 registry()->GetFinalReleaseCallback(DATABASE_ID_0, BLOB_KEY_0); | |
155 | |
156 add_ref.Run(); | |
157 RunUntilIdle(); | |
158 | |
159 EXPECT_TRUE(factory()->CheckSingleOriginInUse(backing_store()->origin_url())); | |
160 EXPECT_TRUE(backing_store()->CheckUnusedBlobsEmpty()); | |
161 | |
162 EXPECT_TRUE(registry()->MarkDeletedCheckIfUsed(DATABASE_ID_0, BLOB_KEY_0)); | |
163 RunUntilIdle(); | |
164 | |
165 EXPECT_TRUE(factory()->CheckSingleOriginInUse(backing_store()->origin_url())); | |
166 EXPECT_TRUE(backing_store()->CheckUnusedBlobsEmpty()); | |
167 | |
168 release.Run(base::FilePath()); | |
169 RunUntilIdle(); | |
170 | |
171 EXPECT_TRUE(factory()->CheckNoOriginsInUse()); | |
172 EXPECT_TRUE( | |
173 backing_store()->CheckSingleUnusedBlob(DATABASE_ID_0, BLOB_KEY_0)); | |
174 } | |
175 | |
176 TEST_F(IndexedDBActiveBlobRegistryTest, MultipleBlobs) { | |
177 EXPECT_TRUE(factory()->CheckNoOriginsInUse()); | |
178 EXPECT_TRUE(backing_store()->CheckUnusedBlobsEmpty()); | |
179 | |
180 base::Closure add_ref_00 = | |
181 registry()->GetAddBlobRefCallback(DATABASE_ID_0, BLOB_KEY_0); | |
182 ReleaseCallback release_00 = | |
183 registry()->GetFinalReleaseCallback(DATABASE_ID_0, BLOB_KEY_0); | |
184 base::Closure add_ref_01 = | |
185 registry()->GetAddBlobRefCallback(DATABASE_ID_0, BLOB_KEY_1); | |
186 ReleaseCallback release_01 = | |
187 registry()->GetFinalReleaseCallback(DATABASE_ID_0, BLOB_KEY_1); | |
188 base::Closure add_ref_10 = | |
189 registry()->GetAddBlobRefCallback(DATABASE_ID_1, BLOB_KEY_0); | |
190 ReleaseCallback release_10 = | |
191 registry()->GetFinalReleaseCallback(DATABASE_ID_1, BLOB_KEY_0); | |
192 base::Closure add_ref_11 = | |
193 registry()->GetAddBlobRefCallback(DATABASE_ID_1, BLOB_KEY_1); | |
194 ReleaseCallback release_11 = | |
195 registry()->GetFinalReleaseCallback(DATABASE_ID_1, BLOB_KEY_1); | |
196 | |
197 add_ref_00.Run(); | |
198 add_ref_01.Run(); | |
199 RunUntilIdle(); | |
200 | |
201 EXPECT_TRUE(factory()->CheckSingleOriginInUse(backing_store()->origin_url())); | |
202 EXPECT_TRUE(backing_store()->CheckUnusedBlobsEmpty()); | |
203 | |
204 release_00.Run(base::FilePath()); | |
205 add_ref_10.Run(); | |
206 add_ref_11.Run(); | |
207 RunUntilIdle(); | |
208 | |
209 EXPECT_TRUE(factory()->CheckSingleOriginInUse(backing_store()->origin_url())); | |
210 EXPECT_TRUE(backing_store()->CheckUnusedBlobsEmpty()); | |
211 | |
212 EXPECT_TRUE(registry()->MarkDeletedCheckIfUsed(DATABASE_ID_0, BLOB_KEY_1)); | |
213 RunUntilIdle(); | |
214 | |
215 EXPECT_TRUE(factory()->CheckSingleOriginInUse(backing_store()->origin_url())); | |
216 EXPECT_TRUE(backing_store()->CheckUnusedBlobsEmpty()); | |
217 | |
218 release_01.Run(base::FilePath()); | |
219 release_11.Run(base::FilePath()); | |
220 RunUntilIdle(); | |
221 | |
222 EXPECT_TRUE(factory()->CheckSingleOriginInUse(backing_store()->origin_url())); | |
223 EXPECT_TRUE( | |
224 backing_store()->CheckSingleUnusedBlob(DATABASE_ID_0, BLOB_KEY_1)); | |
225 | |
226 release_10.Run(base::FilePath()); | |
227 RunUntilIdle(); | |
228 | |
229 EXPECT_TRUE(factory()->CheckNoOriginsInUse()); | |
230 EXPECT_TRUE( | |
231 backing_store()->CheckSingleUnusedBlob(DATABASE_ID_0, BLOB_KEY_1)); | |
232 } | |
233 | |
234 TEST_F(IndexedDBActiveBlobRegistryTest, ForceShutdown) { | |
235 EXPECT_TRUE(factory()->CheckNoOriginsInUse()); | |
236 EXPECT_TRUE(backing_store()->CheckUnusedBlobsEmpty()); | |
237 | |
238 base::Closure add_ref_0 = | |
239 registry()->GetAddBlobRefCallback(DATABASE_ID_0, BLOB_KEY_0); | |
240 ReleaseCallback release_0 = | |
241 registry()->GetFinalReleaseCallback(DATABASE_ID_0, BLOB_KEY_0); | |
242 base::Closure add_ref_1 = | |
243 registry()->GetAddBlobRefCallback(DATABASE_ID_0, BLOB_KEY_1); | |
244 ReleaseCallback release_1 = | |
245 registry()->GetFinalReleaseCallback(DATABASE_ID_0, BLOB_KEY_1); | |
246 | |
247 add_ref_0.Run(); | |
248 RunUntilIdle(); | |
249 | |
250 EXPECT_TRUE(factory()->CheckSingleOriginInUse(backing_store()->origin_url())); | |
251 EXPECT_TRUE(backing_store()->CheckUnusedBlobsEmpty()); | |
252 | |
253 registry()->ForceShutdown(); | |
254 | |
255 add_ref_1.Run(); | |
256 RunUntilIdle(); | |
257 | |
258 // Nothing changes. | |
259 EXPECT_TRUE(factory()->CheckSingleOriginInUse(backing_store()->origin_url())); | |
260 EXPECT_TRUE(backing_store()->CheckUnusedBlobsEmpty()); | |
261 | |
262 // Nothing's marked as in use any more. | |
263 EXPECT_FALSE(registry()->MarkDeletedCheckIfUsed(DATABASE_ID_0, BLOB_KEY_1)); | |
264 RunUntilIdle(); | |
265 | |
266 // Nothing changes. | |
267 EXPECT_TRUE(factory()->CheckSingleOriginInUse(backing_store()->origin_url())); | |
268 EXPECT_TRUE(backing_store()->CheckUnusedBlobsEmpty()); | |
269 | |
270 release_0.Run(base::FilePath()); | |
271 release_1.Run(base::FilePath()); | |
272 RunUntilIdle(); | |
273 | |
274 // Nothing changes. | |
275 EXPECT_TRUE(factory()->CheckSingleOriginInUse(backing_store()->origin_url())); | |
276 EXPECT_TRUE(backing_store()->CheckUnusedBlobsEmpty()); | |
277 } | |
278 | |
279 } // namespace | |
280 | |
281 } // namespace content | |
OLD | NEW |