|
|
@@ -40,6 +40,15 @@ static void partialUpload(FakeFolder &fakeFolder, const QString &name, int size)
|
|
|
[](int s, const FileInfo &i) { return s + i.size; }));
|
|
|
}
|
|
|
|
|
|
+// Reduce max chunk size a bit so we get more chunks
|
|
|
+static void setChunkSize(SyncEngine &engine, quint64 size)
|
|
|
+{
|
|
|
+ SyncOptions options;
|
|
|
+ options._maxChunkSize = size;
|
|
|
+ options._initialChunkSize = size;
|
|
|
+ options._minChunkSize = size;
|
|
|
+ engine.setSyncOptions(options);
|
|
|
+}
|
|
|
|
|
|
class TestChunkingNG : public QObject
|
|
|
{
|
|
|
@@ -50,7 +59,9 @@ private slots:
|
|
|
void testFileUpload() {
|
|
|
FakeFolder fakeFolder{FileInfo::A12_B12_C12_S12()};
|
|
|
fakeFolder.syncEngine().account()->setCapabilities({ { "dav", QVariantMap{ {"chunking", "1.0"} } } });
|
|
|
- const int size = 300 * 1000 * 1000; // 300 MB
|
|
|
+ setChunkSize(fakeFolder.syncEngine(), 1 * 1000 * 1000);
|
|
|
+ const int size = 10 * 1000 * 1000; // 10 MB
|
|
|
+
|
|
|
fakeFolder.localModifier().insert("A/a0", size);
|
|
|
QVERIFY(fakeFolder.syncOnce());
|
|
|
QCOMPARE(fakeFolder.currentLocalState(), fakeFolder.currentRemoteState());
|
|
|
@@ -68,13 +79,15 @@ private slots:
|
|
|
void testResume1() {
|
|
|
FakeFolder fakeFolder{FileInfo::A12_B12_C12_S12()};
|
|
|
fakeFolder.syncEngine().account()->setCapabilities({ { "dav", QVariantMap{ {"chunking", "1.0"} } } });
|
|
|
- const int size = 300 * 1000 * 1000; // 300 MB
|
|
|
+ const int size = 10 * 1000 * 1000; // 10 MB
|
|
|
+ setChunkSize(fakeFolder.syncEngine(), 1 * 1000 * 1000);
|
|
|
+
|
|
|
partialUpload(fakeFolder, "A/a0", size);
|
|
|
QCOMPARE(fakeFolder.uploadState().children.count(), 1);
|
|
|
auto chunkingId = fakeFolder.uploadState().children.first().name;
|
|
|
const auto &chunkMap = fakeFolder.uploadState().children.first().children;
|
|
|
quint64 uploadedSize = std::accumulate(chunkMap.begin(), chunkMap.end(), 0LL, [](quint64 s, const FileInfo &f) { return s + f.size; });
|
|
|
- QVERIFY(uploadedSize > 50 * 1000 * 1000); // at least 50 MB
|
|
|
+ QVERIFY(uploadedSize > 2 * 1000 * 1000); // at least 2 MB
|
|
|
|
|
|
// Add a fake chunk to make sure it gets deleted
|
|
|
fakeFolder.uploadState().children.first().insert("10000", size);
|
|
|
@@ -102,19 +115,14 @@ private slots:
|
|
|
void testResume2() {
|
|
|
FakeFolder fakeFolder{FileInfo::A12_B12_C12_S12()};
|
|
|
fakeFolder.syncEngine().account()->setCapabilities({ { "dav", QVariantMap{ {"chunking", "1.0"} } } });
|
|
|
-
|
|
|
- // Reduce max chunk size a bit so we get more chunks
|
|
|
- SyncOptions options;
|
|
|
- options._maxChunkSize = 30 * 1000 * 1000;
|
|
|
- fakeFolder.syncEngine().setSyncOptions(options);
|
|
|
-
|
|
|
- const int size = 300 * 1000 * 1000; // 300 MB
|
|
|
+ setChunkSize(fakeFolder.syncEngine(), 1 * 1000 * 1000);
|
|
|
+ const int size = 150 * 1000 * 1000; // 30 MB
|
|
|
partialUpload(fakeFolder, "A/a0", size);
|
|
|
QCOMPARE(fakeFolder.uploadState().children.count(), 1);
|
|
|
auto chunkingId = fakeFolder.uploadState().children.first().name;
|
|
|
const auto &chunkMap = fakeFolder.uploadState().children.first().children;
|
|
|
quint64 uploadedSize = std::accumulate(chunkMap.begin(), chunkMap.end(), 0LL, [](quint64 s, const FileInfo &f) { return s + f.size; });
|
|
|
- QVERIFY(uploadedSize > 50 * 1000 * 1000); // at least 50 MB
|
|
|
+ QVERIFY(uploadedSize > 2 * 1000 * 1000); // at least 50 MB
|
|
|
QVERIFY(chunkMap.size() >= 3); // at least three chunks
|
|
|
|
|
|
QStringList chunksToDelete;
|
|
|
@@ -162,13 +170,15 @@ private slots:
|
|
|
void testResume3() {
|
|
|
FakeFolder fakeFolder{FileInfo::A12_B12_C12_S12()};
|
|
|
fakeFolder.syncEngine().account()->setCapabilities({ { "dav", QVariantMap{ {"chunking", "1.0"} } } });
|
|
|
- const int size = 300 * 1000 * 1000; // 300 MB
|
|
|
+ const int size = 30 * 1000 * 1000; // 30 MB
|
|
|
+ setChunkSize(fakeFolder.syncEngine(), 1 * 1000 * 1000);
|
|
|
+
|
|
|
partialUpload(fakeFolder, "A/a0", size);
|
|
|
QCOMPARE(fakeFolder.uploadState().children.count(), 1);
|
|
|
auto chunkingId = fakeFolder.uploadState().children.first().name;
|
|
|
const auto &chunkMap = fakeFolder.uploadState().children.first().children;
|
|
|
quint64 uploadedSize = std::accumulate(chunkMap.begin(), chunkMap.end(), 0LL, [](quint64 s, const FileInfo &f) { return s + f.size; });
|
|
|
- QVERIFY(uploadedSize > 50 * 1000 * 1000); // at least 50 MB
|
|
|
+ QVERIFY(uploadedSize > 5 * 1000 * 1000); // at least 5 MB
|
|
|
|
|
|
// Add a chunk that makes the file completely uploaded
|
|
|
fakeFolder.uploadState().children.first().insert(
|
|
|
@@ -205,13 +215,15 @@ private slots:
|
|
|
void testResume4() {
|
|
|
FakeFolder fakeFolder{FileInfo::A12_B12_C12_S12()};
|
|
|
fakeFolder.syncEngine().account()->setCapabilities({ { "dav", QVariantMap{ {"chunking", "1.0"} } } });
|
|
|
- const int size = 300 * 1000 * 1000; // 300 MB
|
|
|
+ const int size = 30 * 1000 * 1000; // 300 MB
|
|
|
+ setChunkSize(fakeFolder.syncEngine(), 1 * 1000 * 1000);
|
|
|
+
|
|
|
partialUpload(fakeFolder, "A/a0", size);
|
|
|
QCOMPARE(fakeFolder.uploadState().children.count(), 1);
|
|
|
auto chunkingId = fakeFolder.uploadState().children.first().name;
|
|
|
const auto &chunkMap = fakeFolder.uploadState().children.first().children;
|
|
|
quint64 uploadedSize = std::accumulate(chunkMap.begin(), chunkMap.end(), 0LL, [](quint64 s, const FileInfo &f) { return s + f.size; });
|
|
|
- QVERIFY(uploadedSize > 50 * 1000 * 1000); // at least 50 MB
|
|
|
+ QVERIFY(uploadedSize > 5 * 1000 * 1000); // at least 5 MB
|
|
|
|
|
|
// Add a chunk that makes the file more than completely uploaded
|
|
|
fakeFolder.uploadState().children.first().insert(
|
|
|
@@ -232,13 +244,14 @@ private slots:
|
|
|
{
|
|
|
FakeFolder fakeFolder{ FileInfo::A12_B12_C12_S12() };
|
|
|
fakeFolder.syncEngine().account()->setCapabilities({ { "dav", QVariantMap{ { "chunking", "1.0" } } }, { "checksums", QVariantMap{ { "supportedTypes", QStringList() << "SHA1" } } } });
|
|
|
- const int size = 150 * 1000 * 1000;
|
|
|
+ const int size = 15 * 1000 * 1000;
|
|
|
+ setChunkSize(fakeFolder.syncEngine(), 1 * 1000 * 1000);
|
|
|
|
|
|
// Make the MOVE never reply, but trigger a client-abort and apply the change remotely
|
|
|
auto parent = new QObject;
|
|
|
QByteArray moveChecksumHeader;
|
|
|
int nGET = 0;
|
|
|
- int responseDelay = 10000; // bigger than abort-wait timeout
|
|
|
+ int responseDelay = 100000; // bigger than abort-wait timeout
|
|
|
fakeFolder.setServerOverride([&](QNetworkAccessManager::Operation op, const QNetworkRequest &request, QIODevice *) -> QNetworkReply * {
|
|
|
if (request.attribute(QNetworkRequest::CustomVerbAttribute) == "MOVE") {
|
|
|
QTimer::singleShot(50, parent, [&]() { fakeFolder.syncEngine().abort(); });
|
|
|
@@ -315,11 +328,12 @@ private slots:
|
|
|
{
|
|
|
FakeFolder fakeFolder{ FileInfo::A12_B12_C12_S12() };
|
|
|
fakeFolder.syncEngine().account()->setCapabilities({ { "dav", QVariantMap{ { "chunking", "1.0" } } }, { "checksums", QVariantMap{ { "supportedTypes", QStringList() << "SHA1" } } } });
|
|
|
- const int size = 150 * 1000 * 1000;
|
|
|
+ const int size = 15 * 1000 * 1000;
|
|
|
+ setChunkSize(fakeFolder.syncEngine(), 1 * 1000 * 1000);
|
|
|
|
|
|
// Make the MOVE never reply, but trigger a client-abort and apply the change remotely
|
|
|
auto parent = new QObject;
|
|
|
- int responseDelay = 2000; // smaller than abort-wait timeout
|
|
|
+ int responseDelay = 200; // smaller than abort-wait timeout
|
|
|
fakeFolder.setServerOverride([&](QNetworkAccessManager::Operation op, const QNetworkRequest &request, QIODevice *) -> QNetworkReply * {
|
|
|
if (request.attribute(QNetworkRequest::CustomVerbAttribute) == "MOVE") {
|
|
|
QTimer::singleShot(50, parent, [&]() { fakeFolder.syncEngine().abort(); });
|
|
|
@@ -328,7 +342,6 @@ private slots:
|
|
|
return nullptr;
|
|
|
});
|
|
|
|
|
|
-
|
|
|
// Test 1: NEW file aborted
|
|
|
fakeFolder.localModifier().insert("A/a0", size);
|
|
|
QVERIFY(fakeFolder.syncOnce());
|
|
|
@@ -345,7 +358,9 @@ private slots:
|
|
|
|
|
|
FakeFolder fakeFolder{FileInfo::A12_B12_C12_S12()};
|
|
|
fakeFolder.syncEngine().account()->setCapabilities({ { "dav", QVariantMap{ {"chunking", "1.0"} } } });
|
|
|
- const int size = 300 * 1000 * 1000; // 300 MB
|
|
|
+ const int size = 10 * 1000 * 1000; // 10 MB
|
|
|
+ setChunkSize(fakeFolder.syncEngine(), 1 * 1000 * 1000);
|
|
|
+
|
|
|
partialUpload(fakeFolder, "A/a0", size);
|
|
|
QCOMPARE(fakeFolder.uploadState().children.count(), 1);
|
|
|
auto chunkingId = fakeFolder.uploadState().children.first().name;
|
|
|
@@ -368,7 +383,9 @@ private slots:
|
|
|
|
|
|
FakeFolder fakeFolder{FileInfo::A12_B12_C12_S12()};
|
|
|
fakeFolder.syncEngine().account()->setCapabilities({ { "dav", QVariantMap{ {"chunking", "1.0"} } } });
|
|
|
- const int size = 300 * 1000 * 1000; // 300 MB
|
|
|
+ const int size = 10 * 1000 * 1000; // 10 MB
|
|
|
+ setChunkSize(fakeFolder.syncEngine(), 1 * 1000 * 1000);
|
|
|
+
|
|
|
partialUpload(fakeFolder, "A/a0", size);
|
|
|
QCOMPARE(fakeFolder.uploadState().children.count(), 1);
|
|
|
|
|
|
@@ -382,7 +399,8 @@ private slots:
|
|
|
void testCreateConflictWhileSyncing() {
|
|
|
FakeFolder fakeFolder{FileInfo::A12_B12_C12_S12()};
|
|
|
fakeFolder.syncEngine().account()->setCapabilities({ { "dav", QVariantMap{ {"chunking", "1.0"} } } });
|
|
|
- const int size = 150 * 1000 * 1000; // 150 MB
|
|
|
+ const int size = 10 * 1000 * 1000; // 10 MB
|
|
|
+ setChunkSize(fakeFolder.syncEngine(), 1 * 1000 * 1000);
|
|
|
|
|
|
// Put a file on the server and download it.
|
|
|
fakeFolder.remoteModifier().insert("A/a0", size);
|
|
|
@@ -437,7 +455,8 @@ private slots:
|
|
|
|
|
|
FakeFolder fakeFolder{FileInfo::A12_B12_C12_S12()};
|
|
|
fakeFolder.syncEngine().account()->setCapabilities({ { "dav", QVariantMap{ {"chunking", "1.0"} } } });
|
|
|
- const int size = 150 * 1000 * 1000; // 150 MB
|
|
|
+ const int size = 10 * 1000 * 1000; // 100 MB
|
|
|
+ setChunkSize(fakeFolder.syncEngine(), 1 * 1000 * 1000);
|
|
|
|
|
|
fakeFolder.localModifier().insert("A/a0", size);
|
|
|
|
|
|
@@ -475,7 +494,8 @@ private slots:
|
|
|
|
|
|
FakeFolder fakeFolder{FileInfo::A12_B12_C12_S12()};
|
|
|
fakeFolder.syncEngine().account()->setCapabilities({ { "dav", QVariantMap{ {"chunking", "1.0"} } } });
|
|
|
- const int size = 300 * 1000 * 1000; // 300 MB
|
|
|
+ const int size = 30 * 1000 * 1000; // 30 MB
|
|
|
+ setChunkSize(fakeFolder.syncEngine(), 1 * 1000 * 1000);
|
|
|
partialUpload(fakeFolder, "A/a0", size);
|
|
|
QCOMPARE(fakeFolder.uploadState().children.count(), 1);
|
|
|
auto chunkingId = fakeFolder.uploadState().children.first().name;
|
|
|
@@ -505,7 +525,8 @@ private slots:
|
|
|
QFETCH(bool, chunking);
|
|
|
FakeFolder fakeFolder{ FileInfo::A12_B12_C12_S12() };
|
|
|
fakeFolder.syncEngine().account()->setCapabilities({ { "dav", QVariantMap{ { "chunking", "1.0" } } }, { "checksums", QVariantMap{ { "supportedTypes", QStringList() << "SHA1" } } } });
|
|
|
- const int size = chunking ? 150 * 1000 * 1000 : 300;
|
|
|
+ const int size = chunking ? 1 * 1000 * 1000 : 300;
|
|
|
+ setChunkSize(fakeFolder.syncEngine(), 300 * 1000);
|
|
|
|
|
|
// Make the MOVE never reply, but trigger a client-abort and apply the change remotely
|
|
|
QByteArray checksumHeader;
|
|
|
@@ -530,7 +551,6 @@ private slots:
|
|
|
return nullptr;
|
|
|
});
|
|
|
|
|
|
-
|
|
|
// Test 1: a NEW file
|
|
|
fakeFolder.localModifier().insert("A/a0", size);
|
|
|
QVERIFY(!fakeFolder.syncOnce()); // timeout!
|