diff options
author | haitaol@chromium.org <haitaol@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2012-10-10 23:36:14 +0000 |
---|---|---|
committer | haitaol@chromium.org <haitaol@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2012-10-10 23:36:14 +0000 |
commit | 734012a12e1ba5539b8ace50dbd59ba5c32c9aef (patch) | |
tree | 7044e917eca83078b4bf178d5376da561b42047b /sync | |
parent | 0e2b516cc74125a97490921751bec186e11ab4eb (diff) | |
download | chromium_src-734012a12e1ba5539b8ace50dbd59ba5c32c9aef.zip chromium_src-734012a12e1ba5539b8ace50dbd59ba5c32c9aef.tar.gz chromium_src-734012a12e1ba5539b8ace50dbd59ba5c32c9aef.tar.bz2 |
[Sync] Add transaction_version to sync DB schema and PersistedKernelInfo. Read/save transactions_version when loading/saving kernel info.
BUG=154858
Review URL: https://chromiumcodereview.appspot.com/11088015
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@161229 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'sync')
-rw-r--r-- | sync/syncable/directory.cc | 2 | ||||
-rw-r--r-- | sync/syncable/directory.h | 7 | ||||
-rw-r--r-- | sync/syncable/directory_backing_store.cc | 44 | ||||
-rw-r--r-- | sync/syncable/directory_backing_store.h | 1 | ||||
-rw-r--r-- | sync/syncable/directory_backing_store_unittest.cc | 28 | ||||
-rw-r--r-- | sync/test/test_directory_backing_store.h | 1 |
6 files changed, 74 insertions, 9 deletions
diff --git a/sync/syncable/directory.cc b/sync/syncable/directory.cc index 4ac17a5..a0a4e24 100644 --- a/sync/syncable/directory.cc +++ b/sync/syncable/directory.cc @@ -83,6 +83,7 @@ Directory::PersistedKernelInfo::PersistedKernelInfo() : next_id(0) { for (int i = FIRST_REAL_MODEL_TYPE; i < MODEL_TYPE_COUNT; ++i) { reset_download_progress(ModelTypeFromInt(i)); + transaction_version[i] = 0; } } @@ -597,6 +598,7 @@ bool Directory::PurgeEntriesWithTypeIn(ModelTypeSet types) { it.Good(); it.Inc()) { set_initial_sync_ended_for_type_unsafe(it.Get(), false); kernel_->persisted_info.reset_download_progress(it.Get()); + kernel_->persisted_info.transaction_version[it.Get()] = 0; } } } diff --git a/sync/syncable/directory.h b/sync/syncable/directory.h index 49d598c..c123e36 100644 --- a/sync/syncable/directory.h +++ b/sync/syncable/directory.h @@ -161,6 +161,13 @@ class Directory { // Last sync timestamp fetched from the server. sync_pb::DataTypeProgressMarker download_progress[MODEL_TYPE_COUNT]; + // Sync-side transaction version per data type. Monotonically incremented + // when updating native model. A copy is also saved in native model. + // Later out-of-sync models can be detected and fixed by comparing + // transaction versions of sync model and native model. + // TODO(hatiaol): implement detection and fixing of out-of-sync models. + // Bug 154858. + int64 transaction_version[MODEL_TYPE_COUNT]; // true iff we ever reached the end of the changelog. ModelTypeSet initial_sync_ended; // The store birthday we were given by the server. Contents are opaque to diff --git a/sync/syncable/directory_backing_store.cc b/sync/syncable/directory_backing_store.cc index fde0279..4f9febf 100644 --- a/sync/syncable/directory_backing_store.cc +++ b/sync/syncable/directory_backing_store.cc @@ -40,7 +40,7 @@ static const string::size_type kUpdateStatementBufferSize = 2048; // Increment this version whenever updating DB tables. extern const int32 kCurrentDBVersion; // Global visibility for our unittest. -const int32 kCurrentDBVersion = 81; +const int32 kCurrentDBVersion = 82; // Iterate over the fields of |entry| and bind each to |statement| for // updating. Returns the number of args bound. @@ -236,8 +236,9 @@ bool DirectoryBackingStore::SaveChanges( sql::Statement s2(db_->GetCachedStatement( SQL_FROM_HERE, "INSERT OR REPLACE " - "INTO models (model_id, progress_marker, initial_sync_ended) " - "VALUES (?, ?, ?)")); + "INTO models (model_id, progress_marker, initial_sync_ended, " + " transaction_version) " + "VALUES (?, ?, ?, ?)")); for (int i = FIRST_REAL_MODEL_TYPE; i < MODEL_TYPE_COUNT; ++i) { // We persist not ModelType but rather a protobuf-derived ID. @@ -247,6 +248,7 @@ bool DirectoryBackingStore::SaveChanges( s2.BindBlob(0, model_id.data(), model_id.length()); s2.BindBlob(1, progress_marker.data(), progress_marker.length()); s2.BindBool(2, info.initial_sync_ended.Has(ModelTypeFromInt(i))); + s2.BindInt64(3, info.transaction_version[i]); if (!s2.Run()) return false; DCHECK_EQ(db_->GetLastChangeCount(), 1); @@ -350,6 +352,12 @@ bool DirectoryBackingStore::InitializeTables() { version_on_disk = 81; } + // Version 82 migration added transaction_version column per data type. + if (version_on_disk == 81) { + if (MigrateVersion81To82()) + version_on_disk = 82; + } + // If one of the migrations requested it, drop columns that aren't current. // It's only safe to do this after migrating all the way to the current // version. @@ -488,8 +496,8 @@ bool DirectoryBackingStore::LoadInfo(Directory::KernelLoadInfo* info) { { sql::Statement s( db_->GetUniqueStatement( - "SELECT model_id, progress_marker, initial_sync_ended " - "FROM models")); + "SELECT model_id, progress_marker, initial_sync_ended, " + "transaction_version FROM models")); while (s.Step()) { ModelType type = ModelIdToModelTypeEnum(s.ColumnBlob(0), @@ -499,6 +507,7 @@ bool DirectoryBackingStore::LoadInfo(Directory::KernelLoadInfo* info) { s.ColumnBlob(1), s.ColumnByteLength(1)); if (s.ColumnBool(2)) info->kernel_info.initial_sync_ended.Put(type); + info->kernel_info.transaction_version[type] = s.ColumnInt64(3); } } if (!s.Succeeded()) @@ -1043,6 +1052,26 @@ bool DirectoryBackingStore::MigrateVersion80To81() { return true; } +bool DirectoryBackingStore::MigrateVersion81To82() { + // Version 82 added transaction_version to kernel info. But if user is + // migrating from 74 or before, 74->75 migration would recreate models table + // that already has transaction_version column. + if (db_->DoesColumnExist("models", "transaction_version")) { + SetVersion(82); + return true; + } + + if (!db_->Execute( + "ALTER TABLE models ADD COLUMN transaction_version BIGINT default 0")) + return false; + sql::Statement update(db_->GetUniqueStatement( + "UPDATE models SET transaction_version = 0")); + if (!update.Run()) + return false; + SetVersion(82); + return true; +} + bool DirectoryBackingStore::CreateTables() { DVLOG(1) << "First run, creating tables"; // Create two little tables share_version and share_info @@ -1141,7 +1170,7 @@ bool DirectoryBackingStore::CreateV71ModelsTable() { } bool DirectoryBackingStore::CreateModelsTable() { - // This is the current schema for the Models table, from version 75 + // This is the current schema for the Models table, from version 81 // onward. If you change the schema, you'll probably want to double-check // the use of this function in the v74-v75 migration. return db_->Execute( @@ -1151,7 +1180,8 @@ bool DirectoryBackingStore::CreateModelsTable() { // Gets set if the syncer ever gets updates from the // server and the server returns 0. Lets us detect the // end of the initial sync. - "initial_sync_ended BOOLEAN default 0)"); + "initial_sync_ended BOOLEAN default 0, " + "transaction_version BIGINT default 0)"); } bool DirectoryBackingStore::CreateShareInfoTable(bool is_temporary) { diff --git a/sync/syncable/directory_backing_store.h b/sync/syncable/directory_backing_store.h index 21bc8c2..ae2b189 100644 --- a/sync/syncable/directory_backing_store.h +++ b/sync/syncable/directory_backing_store.h @@ -156,6 +156,7 @@ class DirectoryBackingStore : public base::NonThreadSafe { bool MigrateVersion78To79(); bool MigrateVersion79To80(); bool MigrateVersion80To81(); + bool MigrateVersion81To82(); scoped_ptr<sql::Connection> db_; sql::Statement save_entry_statement_; diff --git a/sync/syncable/directory_backing_store_unittest.cc b/sync/syncable/directory_backing_store_unittest.cc index 457a702..3cd53c1 100644 --- a/sync/syncable/directory_backing_store_unittest.cc +++ b/sync/syncable/directory_backing_store_unittest.cc @@ -116,10 +116,12 @@ class DirectoryBackingStoreTest : public MigrationTest {}; // Generated via: // -// ruby -ane '$F[1].sub!("LEGACY_", ""); $F[2] = Integer($F[2].sub!("LL", "")) / 10000 - 11644473600000; print "#{$F[0]} #{$F[1]} #{$F[2]}LL\n"' +// ruby -ane '$F[1].sub!("LEGACY_", ""); $F[2] = Integer($F[2].sub!("LL", "")) / +// 10000 - 11644473600000; print "#{$F[0]} #{$F[1]} #{$F[2]}LL"' // // Magic numbers taken from -// http://stackoverflow.com/questions/5398557/java-library-for-dealing-with-win32-filetime . +// http://stackoverflow.com/questions/5398557/ +// java-library-for-dealing-with-win32-filetime . // Now we store them in Java format (ms since the Unix epoch). #define META_PROTO_TIMES_1 1263522064032LL @@ -2370,6 +2372,22 @@ TEST_F(DirectoryBackingStoreTest, DetectInvalidOrdinal) { dbs->Load(&entry_bucket, &kernel_load_info)); } +TEST_F(DirectoryBackingStoreTest, MigrateVersion81To82) { + sql::Connection connection; + ASSERT_TRUE(connection.OpenInMemory()); + SetUpVersion81Database(&connection); + ASSERT_FALSE(connection.DoesColumnExist("models", "transaction_version")); + + scoped_ptr<TestDirectoryBackingStore> dbs( + new TestDirectoryBackingStore(GetUsername(), &connection)); + ASSERT_FALSE(dbs->needs_column_refresh_); + ASSERT_TRUE(dbs->MigrateVersion81To82()); + ASSERT_EQ(82, dbs->GetVersion()); + ASSERT_FALSE(dbs->needs_column_refresh_); + + ASSERT_TRUE(connection.DoesColumnExist("models", "transaction_version")); +} + TEST_P(MigrationTest, ToCurrentVersion) { sql::Connection connection; ASSERT_TRUE(connection.OpenInMemory()); @@ -2416,6 +2434,9 @@ TEST_P(MigrationTest, ToCurrentVersion) { case 80: SetUpVersion80Database(&connection); break; + case 81: + SetUpVersion81Database(&connection); + break; default: // If you see this error, it may mean that you've increased the // database version number but you haven't finished adding unit tests @@ -2495,6 +2516,9 @@ TEST_P(MigrationTest, ToCurrentVersion) { // Column added in version 78. ASSERT_TRUE(connection.DoesColumnExist("metas", "base_server_specifics")); + // Column added in version 82. + ASSERT_TRUE(connection.DoesColumnExist("models", "transaction_version")); + // Check download_progress state (v75 migration) ASSERT_EQ(694, dir_info.kernel_info.download_progress[BOOKMARKS] diff --git a/sync/test/test_directory_backing_store.h b/sync/test/test_directory_backing_store.h index b0e230a..bb90c65 100644 --- a/sync/test/test_directory_backing_store.h +++ b/sync/test/test_directory_backing_store.h @@ -43,6 +43,7 @@ class TestDirectoryBackingStore : public DirectoryBackingStore { FRIEND_TEST_ALL_PREFIXES(DirectoryBackingStoreTest, MigrateVersion78To79); FRIEND_TEST_ALL_PREFIXES(DirectoryBackingStoreTest, MigrateVersion79To80); FRIEND_TEST_ALL_PREFIXES(DirectoryBackingStoreTest, MigrateVersion80To81); + FRIEND_TEST_ALL_PREFIXES(DirectoryBackingStoreTest, MigrateVersion81To82); FRIEND_TEST_ALL_PREFIXES(DirectoryBackingStoreTest, DetectInvalidOrdinal); FRIEND_TEST_ALL_PREFIXES(DirectoryBackingStoreTest, ModelTypeIds); FRIEND_TEST_ALL_PREFIXES(DirectoryBackingStoreTest, Corruption); |