Vfs: Ensure pins change with (de-)hydration

Previously an implicit hydration of a file in an online-only folder
would not change the pin state and cause a dehydration on the next
sync.
This commit is contained in:
Christian Kamm 2019-07-24 15:25:02 +02:00
parent 1ca4942bcf
commit d09c4fd2e8
3 changed files with 55 additions and 6 deletions

View File

@ -1015,11 +1015,11 @@ void PropagateDownloadFile::downloadFinished()
if (_conflictRecord.isValid())
propagator()->_journal->setConflictRecord(_conflictRecord);
if (_item->_type == ItemTypeVirtualFileDownload) {
auto vfs = propagator()->syncOptions()._vfs;
if (vfs && vfs->mode() == Vfs::WithSuffix) {
// If the virtual file used to have a different name and db
// entry, wipe both now.
auto vfs = propagator()->syncOptions()._vfs;
if (vfs && vfs->mode() == Vfs::WithSuffix) {
// entry, remove it transfer its old pin state.
if (_item->_type == ItemTypeVirtualFileDownload) {
QString virtualFile = _item->_file + vfs->fileSuffix();
auto fn = propagator()->getFilePath(virtualFile);
qCDebug(lcPropagateDownload) << "Download of previous virtual file finished" << fn;
@ -1033,6 +1033,11 @@ void PropagateDownloadFile::downloadFinished()
vfs->setPinState(virtualFile, PinState::Inherited);
}
}
// Ensure the pin state isn't contradictory
auto pin = vfs->pinState(_item->_file);
if (pin && *pin == PinState::OnlineOnly)
vfs->setPinState(_item->_file, PinState::Unspecified);
}
updateMetadata(isConflict);

View File

@ -89,6 +89,11 @@ void VfsSuffix::dehydratePlaceholder(const SyncFileItem &item)
setPinState(item._renameTarget, *pin);
setPinState(item._file, PinState::Inherited);
}
// Ensure the pin state isn't contradictory
pin = pinState(item._renameTarget);
if (pin && *pin == PinState::AlwaysLocal)
setPinState(item._renameTarget, PinState::Unspecified);
}
void VfsSuffix::convertToPlaceholder(const QString &, const SyncFileItem &, const QString &)

View File

@ -718,11 +718,11 @@ private slots:
// Case 4: foo -> bar.oc (db unchanged)
fakeFolder.localModifier().rename("case4", "case4-rename" DVSUFFIX);
// Case 5: foo -> bar (db dehydrate)
// Case 5: foo.oc -> bar.oc (db hydrate)
fakeFolder.localModifier().rename("case5" DVSUFFIX, "case5-rename" DVSUFFIX);
triggerDownload(fakeFolder, "case5");
// Case 6: foo.oc -> bar.oc (db hydrate)
// Case 6: foo -> bar (db dehydrate)
fakeFolder.localModifier().rename("case6", "case6-rename");
markForDehydration(fakeFolder, "case6");
@ -1175,6 +1175,45 @@ private slots:
QVERIFY(fakeFolder.currentLocalState().find("onlinerenamed2/file1rename" DVSUFFIX));
QCOMPARE(*vfs->pinState("onlinerenamed2/file1rename" DVSUFFIX), PinState::OnlineOnly);
}
void testIncompatiblePins()
{
FakeFolder fakeFolder{ FileInfo() };
auto vfs = setupVfs(fakeFolder);
QCOMPARE(fakeFolder.currentLocalState(), fakeFolder.currentRemoteState());
auto setPin = [&] (const QByteArray &path, PinState state) {
fakeFolder.syncJournal().internalPinStates().setForPath(path, state);
};
fakeFolder.remoteModifier().mkdir("local");
fakeFolder.remoteModifier().mkdir("online");
QVERIFY(fakeFolder.syncOnce());
QCOMPARE(fakeFolder.currentLocalState(), fakeFolder.currentRemoteState());
setPin("local", PinState::AlwaysLocal);
setPin("online", PinState::OnlineOnly);
fakeFolder.localModifier().insert("local/file1");
fakeFolder.localModifier().insert("online/file1");
QVERIFY(fakeFolder.syncOnce());
markForDehydration(fakeFolder, "local/file1");
triggerDownload(fakeFolder, "online/file1");
// the sync sets the changed files pin states to unspecified
QVERIFY(fakeFolder.syncOnce());
QVERIFY(fakeFolder.currentLocalState().find("online/file1"));
QVERIFY(fakeFolder.currentLocalState().find("local/file1" DVSUFFIX));
QCOMPARE(*vfs->pinState("online/file1"), PinState::Unspecified);
QCOMPARE(*vfs->pinState("local/file1" DVSUFFIX), PinState::Unspecified);
// no change on another sync
QVERIFY(fakeFolder.syncOnce());
QVERIFY(fakeFolder.currentLocalState().find("online/file1"));
QVERIFY(fakeFolder.currentLocalState().find("local/file1" DVSUFFIX));
}
};
QTEST_GUILESS_MAIN(TestSyncVirtualFiles)