Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1119)

Side by Side Diff: content/browser/indexed_db/indexed_db_factory_unittest.cc

Issue 2773823002: Use a two-part data format version in IndexedDB metadata. (Closed)
Patch Set: jsbell, cmumford Created 3 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2013 The Chromium Authors. All rights reserved. 1 // Copyright 2013 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include <stdint.h> 5 #include <stdint.h>
6 #include <utility> 6 #include <utility>
7 7
8 #include "base/files/file_util.h" 8 #include "base/files/file_util.h"
9 #include "base/files/scoped_temp_dir.h" 9 #include "base/files/scoped_temp_dir.h"
10 #include "base/logging.h" 10 #include "base/logging.h"
(...skipping 25 matching lines...) Expand all
36 class MockIDBFactory : public IndexedDBFactoryImpl { 36 class MockIDBFactory : public IndexedDBFactoryImpl {
37 public: 37 public:
38 explicit MockIDBFactory(IndexedDBContextImpl* context) 38 explicit MockIDBFactory(IndexedDBContextImpl* context)
39 : IndexedDBFactoryImpl(context) {} 39 : IndexedDBFactoryImpl(context) {}
40 scoped_refptr<IndexedDBBackingStore> TestOpenBackingStore( 40 scoped_refptr<IndexedDBBackingStore> TestOpenBackingStore(
41 const Origin& origin, 41 const Origin& origin,
42 const base::FilePath& data_directory) { 42 const base::FilePath& data_directory) {
43 IndexedDBDataLossInfo data_loss_info; 43 IndexedDBDataLossInfo data_loss_info;
44 bool disk_full; 44 bool disk_full;
45 leveldb::Status s; 45 leveldb::Status s;
46 scoped_refptr<IndexedDBBackingStore> backing_store = 46 scoped_refptr<IndexedDBBackingStore> backing_store = OpenBackingStore(
47 OpenBackingStore(origin, data_directory, nullptr /* request_context */, 47 origin, data_directory, IndexedDBDataFormatVersion(),
48 &data_loss_info, &disk_full, &s); 48 nullptr /* request_context */, &data_loss_info, &disk_full, &s);
49 EXPECT_EQ(blink::WebIDBDataLossNone, data_loss_info.status); 49 EXPECT_EQ(blink::WebIDBDataLossNone, data_loss_info.status);
50 return backing_store; 50 return backing_store;
51 } 51 }
52 52
53 void TestCloseBackingStore(IndexedDBBackingStore* backing_store) { 53 void TestCloseBackingStore(IndexedDBBackingStore* backing_store) {
54 CloseBackingStore(backing_store->origin()); 54 CloseBackingStore(backing_store->origin());
55 } 55 }
56 56
57 void TestReleaseBackingStore(IndexedDBBackingStore* backing_store, 57 void TestReleaseBackingStore(IndexedDBBackingStore* backing_store,
58 bool immediate) { 58 bool immediate) {
59 ReleaseBackingStore(backing_store->origin(), immediate); 59 ReleaseBackingStore(backing_store->origin(), immediate);
60 } 60 }
61 61
62 private: 62 private:
63 ~MockIDBFactory() override {} 63 ~MockIDBFactory() override {}
64 64
65 DISALLOW_COPY_AND_ASSIGN(MockIDBFactory); 65 DISALLOW_COPY_AND_ASSIGN(MockIDBFactory);
66 }; 66 };
67 67
68 } // namespace 68 } // namespace
69 69
70 class IndexedDBFactoryTest : public testing::Test { 70 class IndexedDBFactoryTest : public testing::Test {
71 public: 71 public:
72 IndexedDBFactoryTest() { 72 void SetUp() override {
73 ASSERT_TRUE(temp_dir_.CreateUniqueTempDir());
73 task_runner_ = new base::TestSimpleTaskRunner(); 74 task_runner_ = new base::TestSimpleTaskRunner();
74 quota_manager_proxy_ = new MockQuotaManagerProxy(nullptr, nullptr); 75 quota_manager_proxy_ = new MockQuotaManagerProxy(nullptr, nullptr);
75 context_ = new IndexedDBContextImpl( 76 context_ = new IndexedDBContextImpl(
76 base::FilePath(), nullptr /* special_storage_policy */, 77 temp_dir_.GetPath(), nullptr /* special_storage_policy */,
77 quota_manager_proxy_.get(), task_runner_.get()); 78 quota_manager_proxy_.get(), task_runner_.get());
78 idb_factory_ = new MockIDBFactory(context_.get()); 79 idb_factory_ = new MockIDBFactory(context_.get());
79 } 80 }
80 ~IndexedDBFactoryTest() override { 81
82 void TearDown() override {
81 quota_manager_proxy_->SimulateQuotaManagerDestroyed(); 83 quota_manager_proxy_->SimulateQuotaManagerDestroyed();
82 } 84 }
83 85
84 protected: 86 protected:
87 IndexedDBFactoryTest() {}
85 MockIDBFactory* factory() const { return idb_factory_.get(); } 88 MockIDBFactory* factory() const { return idb_factory_.get(); }
86 void clear_factory() { idb_factory_ = nullptr; } 89 void clear_factory() { idb_factory_ = nullptr; }
87 IndexedDBContextImpl* context() const { return context_.get(); } 90 IndexedDBContextImpl* context() const { return context_.get(); }
88 91
89 private: 92 private:
93 base::ScopedTempDir temp_dir_;
90 scoped_refptr<base::TestSimpleTaskRunner> task_runner_; 94 scoped_refptr<base::TestSimpleTaskRunner> task_runner_;
91 scoped_refptr<IndexedDBContextImpl> context_; 95 scoped_refptr<IndexedDBContextImpl> context_;
92 scoped_refptr<MockIDBFactory> idb_factory_; 96 scoped_refptr<MockIDBFactory> idb_factory_;
93 scoped_refptr<MockQuotaManagerProxy> quota_manager_proxy_; 97 scoped_refptr<MockQuotaManagerProxy> quota_manager_proxy_;
94 TestBrowserThreadBundle thread_bundle_; 98 TestBrowserThreadBundle thread_bundle_;
95 99
96 DISALLOW_COPY_AND_ASSIGN(IndexedDBFactoryTest); 100 DISALLOW_COPY_AND_ASSIGN(IndexedDBFactoryTest);
97 }; 101 };
98 102
99 TEST_F(IndexedDBFactoryTest, BackingStoreLifetime) { 103 TEST_F(IndexedDBFactoryTest, BackingStoreLifetime) {
(...skipping 106 matching lines...) Expand 10 before | Expand all | Expand 10 after
206 class DiskFullFactory : public IndexedDBFactoryImpl { 210 class DiskFullFactory : public IndexedDBFactoryImpl {
207 public: 211 public:
208 explicit DiskFullFactory(IndexedDBContextImpl* context) 212 explicit DiskFullFactory(IndexedDBContextImpl* context)
209 : IndexedDBFactoryImpl(context) {} 213 : IndexedDBFactoryImpl(context) {}
210 214
211 private: 215 private:
212 ~DiskFullFactory() override {} 216 ~DiskFullFactory() override {}
213 scoped_refptr<IndexedDBBackingStore> OpenBackingStore( 217 scoped_refptr<IndexedDBBackingStore> OpenBackingStore(
214 const Origin& origin, 218 const Origin& origin,
215 const base::FilePath& data_directory, 219 const base::FilePath& data_directory,
220 const IndexedDBDataFormatVersion& data_format_version,
216 scoped_refptr<net::URLRequestContextGetter> request_context_getter, 221 scoped_refptr<net::URLRequestContextGetter> request_context_getter,
217 IndexedDBDataLossInfo* data_loss_info, 222 IndexedDBDataLossInfo* data_loss_info,
218 bool* disk_full, 223 bool* disk_full,
219 leveldb::Status* s) override { 224 leveldb::Status* s) override {
220 *disk_full = true; 225 *disk_full = true;
221 *s = leveldb::Status::IOError("Disk is full"); 226 *s = leveldb::Status::IOError("Disk is full");
222 return scoped_refptr<IndexedDBBackingStore>(); 227 return scoped_refptr<IndexedDBBackingStore>();
223 } 228 }
224 229
225 DISALLOW_COPY_AND_ASSIGN(DiskFullFactory); 230 DISALLOW_COPY_AND_ASSIGN(DiskFullFactory);
(...skipping 26 matching lines...) Expand all
252 scoped_refptr<LookingForQuotaErrorMockCallbacks> callbacks = 257 scoped_refptr<LookingForQuotaErrorMockCallbacks> callbacks =
253 new LookingForQuotaErrorMockCallbacks; 258 new LookingForQuotaErrorMockCallbacks;
254 scoped_refptr<IndexedDBDatabaseCallbacks> dummy_database_callbacks = 259 scoped_refptr<IndexedDBDatabaseCallbacks> dummy_database_callbacks =
255 new IndexedDBDatabaseCallbacks(nullptr, nullptr); 260 new IndexedDBDatabaseCallbacks(nullptr, nullptr);
256 const base::string16 name(ASCIIToUTF16("name")); 261 const base::string16 name(ASCIIToUTF16("name"));
257 std::unique_ptr<IndexedDBPendingConnection> connection( 262 std::unique_ptr<IndexedDBPendingConnection> connection(
258 base::MakeUnique<IndexedDBPendingConnection>( 263 base::MakeUnique<IndexedDBPendingConnection>(
259 callbacks, dummy_database_callbacks, 0 /* child_process_id */, 264 callbacks, dummy_database_callbacks, 0 /* child_process_id */,
260 2 /* transaction_id */, 1 /* version */)); 265 2 /* transaction_id */, 1 /* version */));
261 factory->Open(name, std::move(connection), nullptr /* request_context */, 266 factory->Open(name, std::move(connection), nullptr /* request_context */,
262 origin, temp_directory.GetPath()); 267 origin, temp_directory.GetPath(), IndexedDBDataFormatVersion());
263 EXPECT_TRUE(callbacks->error_called()); 268 EXPECT_TRUE(callbacks->error_called());
264 } 269 }
265 270
266 TEST_F(IndexedDBFactoryTest, BackingStoreReleasedOnForcedClose) { 271 TEST_F(IndexedDBFactoryTest, BackingStoreReleasedOnForcedClose) {
267 const Origin origin(GURL("http://localhost:81")); 272 const Origin origin(GURL("http://localhost:81"));
268 273
269 base::ScopedTempDir temp_directory; 274 base::ScopedTempDir temp_directory;
270 ASSERT_TRUE(temp_directory.CreateUniqueTempDir()); 275 ASSERT_TRUE(temp_directory.CreateUniqueTempDir());
271 276
272 scoped_refptr<MockIndexedDBCallbacks> callbacks(new MockIndexedDBCallbacks()); 277 scoped_refptr<MockIndexedDBCallbacks> callbacks(new MockIndexedDBCallbacks());
273 scoped_refptr<MockIndexedDBDatabaseCallbacks> db_callbacks( 278 scoped_refptr<MockIndexedDBDatabaseCallbacks> db_callbacks(
274 new MockIndexedDBDatabaseCallbacks()); 279 new MockIndexedDBDatabaseCallbacks());
275 const int64_t transaction_id = 1; 280 const int64_t transaction_id = 1;
276 std::unique_ptr<IndexedDBPendingConnection> connection( 281 std::unique_ptr<IndexedDBPendingConnection> connection(
277 base::MakeUnique<IndexedDBPendingConnection>( 282 base::MakeUnique<IndexedDBPendingConnection>(
278 callbacks, db_callbacks, 0 /* child_process_id */, transaction_id, 283 callbacks, db_callbacks, 0 /* child_process_id */, transaction_id,
279 IndexedDBDatabaseMetadata::DEFAULT_VERSION)); 284 IndexedDBDatabaseMetadata::DEFAULT_VERSION));
280 factory()->Open(ASCIIToUTF16("db"), std::move(connection), 285 factory()->Open(ASCIIToUTF16("db"), std::move(connection),
281 nullptr /* request_context */, origin, 286 nullptr /* request_context */, origin,
282 temp_directory.GetPath()); 287 temp_directory.GetPath(), IndexedDBDataFormatVersion());
283 288
284 EXPECT_TRUE(callbacks->connection()); 289 EXPECT_TRUE(callbacks->connection());
285 290
286 EXPECT_TRUE(factory()->IsBackingStoreOpen(origin)); 291 EXPECT_TRUE(factory()->IsBackingStoreOpen(origin));
287 EXPECT_FALSE(factory()->IsBackingStorePendingClose(origin)); 292 EXPECT_FALSE(factory()->IsBackingStorePendingClose(origin));
288 293
289 callbacks->connection()->ForceClose(); 294 callbacks->connection()->ForceClose();
290 295
291 EXPECT_FALSE(factory()->IsBackingStoreOpen(origin)); 296 EXPECT_FALSE(factory()->IsBackingStoreOpen(origin));
292 EXPECT_FALSE(factory()->IsBackingStorePendingClose(origin)); 297 EXPECT_FALSE(factory()->IsBackingStorePendingClose(origin));
293 } 298 }
294 299
295 TEST_F(IndexedDBFactoryTest, BackingStoreReleaseDelayedOnClose) { 300 TEST_F(IndexedDBFactoryTest, BackingStoreReleaseDelayedOnClose) {
296 const Origin origin(GURL("http://localhost:81")); 301 const Origin origin(GURL("http://localhost:81"));
297 302
298 base::ScopedTempDir temp_directory; 303 base::ScopedTempDir temp_directory;
299 ASSERT_TRUE(temp_directory.CreateUniqueTempDir()); 304 ASSERT_TRUE(temp_directory.CreateUniqueTempDir());
300 305
301 scoped_refptr<MockIndexedDBCallbacks> callbacks(new MockIndexedDBCallbacks()); 306 scoped_refptr<MockIndexedDBCallbacks> callbacks(new MockIndexedDBCallbacks());
302 scoped_refptr<MockIndexedDBDatabaseCallbacks> db_callbacks( 307 scoped_refptr<MockIndexedDBDatabaseCallbacks> db_callbacks(
303 new MockIndexedDBDatabaseCallbacks()); 308 new MockIndexedDBDatabaseCallbacks());
304 const int64_t transaction_id = 1; 309 const int64_t transaction_id = 1;
305 std::unique_ptr<IndexedDBPendingConnection> connection( 310 std::unique_ptr<IndexedDBPendingConnection> connection(
306 base::MakeUnique<IndexedDBPendingConnection>( 311 base::MakeUnique<IndexedDBPendingConnection>(
307 callbacks, db_callbacks, 0 /* child_process_id */, transaction_id, 312 callbacks, db_callbacks, 0 /* child_process_id */, transaction_id,
308 IndexedDBDatabaseMetadata::DEFAULT_VERSION)); 313 IndexedDBDatabaseMetadata::DEFAULT_VERSION));
309 factory()->Open(ASCIIToUTF16("db"), std::move(connection), 314 factory()->Open(ASCIIToUTF16("db"), std::move(connection),
310 nullptr /* request_context */, origin, 315 nullptr /* request_context */, origin,
311 temp_directory.GetPath()); 316 temp_directory.GetPath(), IndexedDBDataFormatVersion());
312 317
313 EXPECT_TRUE(callbacks->connection()); 318 EXPECT_TRUE(callbacks->connection());
314 IndexedDBBackingStore* store = 319 IndexedDBBackingStore* store =
315 callbacks->connection()->database()->backing_store(); 320 callbacks->connection()->database()->backing_store();
316 EXPECT_FALSE(store->HasOneRef()); // Factory and database. 321 EXPECT_FALSE(store->HasOneRef()); // Factory and database.
317 322
318 EXPECT_TRUE(factory()->IsBackingStoreOpen(origin)); 323 EXPECT_TRUE(factory()->IsBackingStoreOpen(origin));
319 callbacks->connection()->Close(); 324 callbacks->connection()->Close();
320 EXPECT_TRUE(store->HasOneRef()); // Factory. 325 EXPECT_TRUE(store->HasOneRef()); // Factory.
321 EXPECT_TRUE(factory()->IsBackingStoreOpen(origin)); 326 EXPECT_TRUE(factory()->IsBackingStoreOpen(origin));
(...skipping 16 matching lines...) Expand all
338 base::ScopedTempDir temp_directory; 343 base::ScopedTempDir temp_directory;
339 ASSERT_TRUE(temp_directory.CreateUniqueTempDir()); 344 ASSERT_TRUE(temp_directory.CreateUniqueTempDir());
340 345
341 EXPECT_FALSE(factory()->IsBackingStoreOpen(origin)); 346 EXPECT_FALSE(factory()->IsBackingStoreOpen(origin));
342 347
343 const bool expect_connection = false; 348 const bool expect_connection = false;
344 scoped_refptr<MockIndexedDBCallbacks> callbacks( 349 scoped_refptr<MockIndexedDBCallbacks> callbacks(
345 new MockIndexedDBCallbacks(expect_connection)); 350 new MockIndexedDBCallbacks(expect_connection));
346 factory()->DeleteDatabase(ASCIIToUTF16("db"), nullptr /* request_context */, 351 factory()->DeleteDatabase(ASCIIToUTF16("db"), nullptr /* request_context */,
347 callbacks, origin, temp_directory.GetPath(), 352 callbacks, origin, temp_directory.GetPath(),
353 IndexedDBDataFormatVersion(),
348 false /* force_close */); 354 false /* force_close */);
349 355
350 EXPECT_TRUE(factory()->IsBackingStoreOpen(origin)); 356 EXPECT_TRUE(factory()->IsBackingStoreOpen(origin));
351 EXPECT_TRUE(factory()->IsBackingStorePendingClose(origin)); 357 EXPECT_TRUE(factory()->IsBackingStorePendingClose(origin));
352 358
353 // Now simulate shutdown, which should stop the timer. 359 // Now simulate shutdown, which should stop the timer.
354 factory()->ContextDestroyed(); 360 factory()->ContextDestroyed();
355 361
356 EXPECT_FALSE(factory()->IsBackingStoreOpen(origin)); 362 EXPECT_FALSE(factory()->IsBackingStoreOpen(origin));
357 EXPECT_FALSE(factory()->IsBackingStorePendingClose(origin)); 363 EXPECT_FALSE(factory()->IsBackingStorePendingClose(origin));
358 } 364 }
359 365
360 TEST_F(IndexedDBFactoryTest, GetDatabaseNamesClosesBackingStore) { 366 TEST_F(IndexedDBFactoryTest, GetDatabaseNamesClosesBackingStore) {
361 const Origin origin(GURL("http://localhost:81")); 367 const Origin origin(GURL("http://localhost:81"));
362 368
363 base::ScopedTempDir temp_directory; 369 base::ScopedTempDir temp_directory;
364 ASSERT_TRUE(temp_directory.CreateUniqueTempDir()); 370 ASSERT_TRUE(temp_directory.CreateUniqueTempDir());
365 371
366 EXPECT_FALSE(factory()->IsBackingStoreOpen(origin)); 372 EXPECT_FALSE(factory()->IsBackingStoreOpen(origin));
367 373
368 const bool expect_connection = false; 374 const bool expect_connection = false;
369 scoped_refptr<MockIndexedDBCallbacks> callbacks( 375 scoped_refptr<MockIndexedDBCallbacks> callbacks(
370 new MockIndexedDBCallbacks(expect_connection)); 376 new MockIndexedDBCallbacks(expect_connection));
371 factory()->GetDatabaseNames(callbacks, origin, temp_directory.GetPath(), 377 factory()->GetDatabaseNames(callbacks, origin, temp_directory.GetPath(),
378 IndexedDBDataFormatVersion(),
372 nullptr /* request_context */); 379 nullptr /* request_context */);
373 380
374 EXPECT_TRUE(factory()->IsBackingStoreOpen(origin)); 381 EXPECT_TRUE(factory()->IsBackingStoreOpen(origin));
375 EXPECT_TRUE(factory()->IsBackingStorePendingClose(origin)); 382 EXPECT_TRUE(factory()->IsBackingStorePendingClose(origin));
376 383
377 // Now simulate shutdown, which should stop the timer. 384 // Now simulate shutdown, which should stop the timer.
378 factory()->ContextDestroyed(); 385 factory()->ContextDestroyed();
379 386
380 EXPECT_FALSE(factory()->IsBackingStoreOpen(origin)); 387 EXPECT_FALSE(factory()->IsBackingStoreOpen(origin));
381 EXPECT_FALSE(factory()->IsBackingStorePendingClose(origin)); 388 EXPECT_FALSE(factory()->IsBackingStorePendingClose(origin));
382 } 389 }
383 390
384 TEST_F(IndexedDBFactoryTest, ForceCloseReleasesBackingStore) { 391 TEST_F(IndexedDBFactoryTest, ForceCloseReleasesBackingStore) {
385 const Origin origin(GURL("http://localhost:81")); 392 const Origin origin(GURL("http://localhost:81"));
386 393
387 base::ScopedTempDir temp_directory; 394 base::ScopedTempDir temp_directory;
388 ASSERT_TRUE(temp_directory.CreateUniqueTempDir()); 395 ASSERT_TRUE(temp_directory.CreateUniqueTempDir());
389 396
390 scoped_refptr<MockIndexedDBCallbacks> callbacks(new MockIndexedDBCallbacks()); 397 scoped_refptr<MockIndexedDBCallbacks> callbacks(new MockIndexedDBCallbacks());
391 scoped_refptr<MockIndexedDBDatabaseCallbacks> db_callbacks( 398 scoped_refptr<MockIndexedDBDatabaseCallbacks> db_callbacks(
392 new MockIndexedDBDatabaseCallbacks()); 399 new MockIndexedDBDatabaseCallbacks());
393 const int64_t transaction_id = 1; 400 const int64_t transaction_id = 1;
394 std::unique_ptr<IndexedDBPendingConnection> connection( 401 std::unique_ptr<IndexedDBPendingConnection> connection(
395 base::MakeUnique<IndexedDBPendingConnection>( 402 base::MakeUnique<IndexedDBPendingConnection>(
396 callbacks, db_callbacks, 0 /* child_process_id */, transaction_id, 403 callbacks, db_callbacks, 0 /* child_process_id */, transaction_id,
397 IndexedDBDatabaseMetadata::DEFAULT_VERSION)); 404 IndexedDBDatabaseMetadata::DEFAULT_VERSION));
398 factory()->Open(ASCIIToUTF16("db"), std::move(connection), 405 factory()->Open(ASCIIToUTF16("db"), std::move(connection),
399 nullptr /* request_context */, origin, 406 nullptr /* request_context */, origin,
400 temp_directory.GetPath()); 407 temp_directory.GetPath(), IndexedDBDataFormatVersion());
401 408
402 EXPECT_TRUE(callbacks->connection()); 409 EXPECT_TRUE(callbacks->connection());
403 EXPECT_TRUE(factory()->IsBackingStoreOpen(origin)); 410 EXPECT_TRUE(factory()->IsBackingStoreOpen(origin));
404 EXPECT_FALSE(factory()->IsBackingStorePendingClose(origin)); 411 EXPECT_FALSE(factory()->IsBackingStorePendingClose(origin));
405 412
406 callbacks->connection()->Close(); 413 callbacks->connection()->Close();
407 414
408 EXPECT_TRUE(factory()->IsBackingStoreOpen(origin)); 415 EXPECT_TRUE(factory()->IsBackingStoreOpen(origin));
409 EXPECT_TRUE(factory()->IsBackingStorePendingClose(origin)); 416 EXPECT_TRUE(factory()->IsBackingStorePendingClose(origin));
410 417
(...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after
472 // Open at version 2, then close. 479 // Open at version 2, then close.
473 { 480 {
474 scoped_refptr<UpgradeNeededCallbacks> callbacks( 481 scoped_refptr<UpgradeNeededCallbacks> callbacks(
475 new UpgradeNeededCallbacks()); 482 new UpgradeNeededCallbacks());
476 std::unique_ptr<IndexedDBPendingConnection> connection( 483 std::unique_ptr<IndexedDBPendingConnection> connection(
477 base::MakeUnique<IndexedDBPendingConnection>( 484 base::MakeUnique<IndexedDBPendingConnection>(
478 callbacks, db_callbacks, 0 /* child_process_id */, transaction_id, 485 callbacks, db_callbacks, 0 /* child_process_id */, transaction_id,
479 db_version)); 486 db_version));
480 factory()->Open(db_name, std::move(connection), 487 factory()->Open(db_name, std::move(connection),
481 nullptr /* request_context */, origin, 488 nullptr /* request_context */, origin,
482 temp_directory.GetPath()); 489 temp_directory.GetPath(), IndexedDBDataFormatVersion());
483 EXPECT_TRUE(factory()->IsDatabaseOpen(origin, db_name)); 490 EXPECT_TRUE(factory()->IsDatabaseOpen(origin, db_name));
484 491
485 // Pump the message loop so the upgrade transaction can run. 492 // Pump the message loop so the upgrade transaction can run.
486 base::RunLoop().RunUntilIdle(); 493 base::RunLoop().RunUntilIdle();
487 EXPECT_TRUE(callbacks->connection()); 494 EXPECT_TRUE(callbacks->connection());
488 callbacks->connection()->database()->Commit( 495 callbacks->connection()->database()->Commit(
489 callbacks->connection()->GetTransaction(transaction_id)); 496 callbacks->connection()->GetTransaction(transaction_id));
490 497
491 callbacks->connection()->Close(); 498 callbacks->connection()->Close();
492 EXPECT_FALSE(factory()->IsDatabaseOpen(origin, db_name)); 499 EXPECT_FALSE(factory()->IsDatabaseOpen(origin, db_name));
493 } 500 }
494 501
495 // Open at version < 2, which will fail; ensure factory doesn't retain 502 // Open at version < 2, which will fail; ensure factory doesn't retain
496 // the database object. 503 // the database object.
497 { 504 {
498 scoped_refptr<ErrorCallbacks> callbacks(new ErrorCallbacks()); 505 scoped_refptr<ErrorCallbacks> callbacks(new ErrorCallbacks());
499 std::unique_ptr<IndexedDBPendingConnection> connection( 506 std::unique_ptr<IndexedDBPendingConnection> connection(
500 base::MakeUnique<IndexedDBPendingConnection>( 507 base::MakeUnique<IndexedDBPendingConnection>(
501 callbacks, db_callbacks, 0 /* child_process_id */, transaction_id, 508 callbacks, db_callbacks, 0 /* child_process_id */, transaction_id,
502 db_version - 1)); 509 db_version - 1));
503 factory()->Open(db_name, std::move(connection), 510 factory()->Open(db_name, std::move(connection),
504 nullptr /* request_context */, origin, 511 nullptr /* request_context */, origin,
505 temp_directory.GetPath()); 512 temp_directory.GetPath(), IndexedDBDataFormatVersion());
506 EXPECT_TRUE(callbacks->saw_error()); 513 EXPECT_TRUE(callbacks->saw_error());
507 EXPECT_FALSE(factory()->IsDatabaseOpen(origin, db_name)); 514 EXPECT_FALSE(factory()->IsDatabaseOpen(origin, db_name));
508 } 515 }
509 516
510 // Terminate all pending-close timers. 517 // Terminate all pending-close timers.
511 factory()->ForceClose(origin); 518 factory()->ForceClose(origin);
512 } 519 }
520 namespace {
521
522 class DataLossCallbacks final : public MockIndexedDBCallbacks {
523 public:
524 blink::WebIDBDataLoss data_loss() const { return data_loss_; }
525 void OnSuccess(std::unique_ptr<IndexedDBConnection> connection,
526 const IndexedDBDatabaseMetadata& metadata) override {
527 if (!connection_)
528 connection_ = std::move(connection);
529 }
530 void OnError(const IndexedDBDatabaseError& error) final {
531 ADD_FAILURE() << "Unexpected IDB error: " << error.message();
532 }
533 void OnUpgradeNeeded(int64_t old_version,
534 std::unique_ptr<IndexedDBConnection> connection,
535 const content::IndexedDBDatabaseMetadata& metadata,
536 const IndexedDBDataLossInfo& data_loss) final {
537 connection_ = std::move(connection);
538 data_loss_ = data_loss.status;
539 }
540
541 private:
542 ~DataLossCallbacks() final {}
543 blink::WebIDBDataLoss data_loss_ = blink::WebIDBDataLossNone;
544 };
545
546 TEST_F(IndexedDBFactoryTest, DataFormatVersion) {
547 auto try_open = [this](const Origin& origin,
548 const IndexedDBDataFormatVersion& version) {
549 auto db_callbacks = make_scoped_refptr(new MockIndexedDBDatabaseCallbacks);
550 auto callbacks = make_scoped_refptr(new DataLossCallbacks);
551 const int64_t transaction_id = 1;
552 factory()->Open(ASCIIToUTF16("test_db"),
553 base::MakeUnique<IndexedDBPendingConnection>(
554 callbacks, db_callbacks, 0 /* child_process_id */,
555 transaction_id, 1 /* version */),
556 nullptr /* request_context */, origin,
557 context()->data_path(), version);
558 base::RunLoop().RunUntilIdle();
559 auto* connection = callbacks->connection();
560 EXPECT_TRUE(connection);
561 connection->database()->Commit(connection->GetTransaction(transaction_id));
562 connection->Close();
563 factory()->ForceClose(origin);
564 return callbacks->data_loss();
565 };
566
567 using blink::WebIDBDataLossNone;
568 using blink::WebIDBDataLossTotal;
569 const struct {
570 const char* origin;
571 IndexedDBDataFormatVersion open_version_1;
572 IndexedDBDataFormatVersion open_version_2;
573 blink::WebIDBDataLoss expected_data_loss;
574 } kTestCases[] = {
575 {"http://same-version.com/", {3, 4}, {3, 4}, WebIDBDataLossNone},
576 {"http://blink-upgrade.com/", {3, 4}, {3, 5}, WebIDBDataLossNone},
577 {"http://v8-upgrade.com/", {3, 4}, {4, 4}, WebIDBDataLossNone},
578 {"http://both-upgrade.com/", {3, 4}, {4, 5}, WebIDBDataLossNone},
579 {"http://blink-downgrade.com/", {3, 4}, {3, 3}, WebIDBDataLossTotal},
580 {"http://v8-downgrade.com/", {3, 4}, {2, 4}, WebIDBDataLossTotal},
581 {"http://both-downgrade.com/", {3, 4}, {2, 3}, WebIDBDataLossTotal},
582 {"http://v8-up-blink-down.com/", {3, 4}, {4, 2}, WebIDBDataLossTotal},
583 {"http://v8-down-blink-up.com/", {3, 4}, {2, 5}, WebIDBDataLossTotal},
584 };
585 for (const auto& test : kTestCases) {
586 SCOPED_TRACE(test.origin);
587 const Origin origin(GURL(test.origin));
588 ASSERT_EQ(WebIDBDataLossNone, try_open(origin, test.open_version_1));
589 EXPECT_EQ(test.expected_data_loss, try_open(origin, test.open_version_2));
590 }
591 }
592
593 } // namespace
513 594
514 } // namespace content 595 } // namespace content
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698