aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMarco Bubke <marco.bubke@qt.io>2022-01-11 14:52:38 +0100
committerMarco Bubke <marco.bubke@qt.io>2022-01-12 16:27:08 +0000
commit68ac61193ca09bd52b4bd3a5f1f5193afa52f1d1 (patch)
tree20cf7bee8e8db4435437d1b1a384970f9d45d37e
parent7ce13691ff2764e317f357fac4931e7bc16d8091 (diff)
QmlDesigner: Refresh preview image every hour
It is to assumed that the preview image will be changed and we don't need to collect the time stamps of the files. Task-number: QDS-5924 Change-Id: Icf5540d7bcc9da17a1497641f6189f35eb47f5d2 Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org> Reviewed-by: <github-actions-qt-creator@cristianadam.eu> Reviewed-by: Thomas Hartmann <thomas.hartmann@qt.io>
-rw-r--r--src/libs/sqlite/sqlitetimestamp.h11
-rw-r--r--src/plugins/qmldesigner/designercore/imagecache/asynchronousimagefactory.cpp6
-rw-r--r--src/plugins/qmldesigner/designercore/imagecache/timestampprovider.h1
-rw-r--r--src/plugins/qmldesigner/designercore/imagecache/timestampproviderinterface.h1
-rw-r--r--src/plugins/qmldesigner/qmldesignerprojectmanager.cpp19
-rw-r--r--tests/unit/unittest/asynchronousimagefactory-test.cpp48
-rw-r--r--tests/unit/unittest/mocktimestampprovider.h1
7 files changed, 82 insertions, 5 deletions
diff --git a/src/libs/sqlite/sqlitetimestamp.h b/src/libs/sqlite/sqlitetimestamp.h
index c7c100ec45..eb98d8852c 100644
--- a/src/libs/sqlite/sqlitetimestamp.h
+++ b/src/libs/sqlite/sqlitetimestamp.h
@@ -41,6 +41,17 @@ public:
}
friend bool operator!=(TimeStamp first, TimeStamp second) { return !(first == second); }
+ friend bool operator<(TimeStamp first, TimeStamp second) { return first.value < second.value; }
+
+ friend TimeStamp operator+(TimeStamp first, TimeStamp second)
+ {
+ return first.value + second.value;
+ }
+
+ friend TimeStamp operator-(TimeStamp first, TimeStamp second)
+ {
+ return first.value - second.value;
+ }
bool isValid() const { return value >= 0; }
diff --git a/src/plugins/qmldesigner/designercore/imagecache/asynchronousimagefactory.cpp b/src/plugins/qmldesigner/designercore/imagecache/asynchronousimagefactory.cpp
index 81c7aa53ee..83cc937230 100644
--- a/src/plugins/qmldesigner/designercore/imagecache/asynchronousimagefactory.cpp
+++ b/src/plugins/qmldesigner/designercore/imagecache/asynchronousimagefactory.cpp
@@ -28,7 +28,7 @@
#include "imagecachecollector.h"
#include "imagecachegenerator.h"
#include "imagecachestorage.h"
-#include "timestampprovider.h"
+#include "timestampproviderinterface.h"
namespace QmlDesigner {
@@ -116,9 +116,11 @@ void AsynchronousImageFactory::request(Utils::SmallStringView name,
const auto currentModifiedTime = timeStampProvider.timeStamp(name);
const auto storageModifiedTime = storage.fetchModifiedImageTime(id);
+ const auto pause = timeStampProvider.pause();
- if (currentModifiedTime == storageModifiedTime)
+ if (currentModifiedTime < (storageModifiedTime + pause))
return;
+
auto capture = [=](const QImage &image, const QImage &smallImage) {
m_storage.storeImage(id, currentModifiedTime, image, smallImage);
};
diff --git a/src/plugins/qmldesigner/designercore/imagecache/timestampprovider.h b/src/plugins/qmldesigner/designercore/imagecache/timestampprovider.h
index 8acc5fcb58..e9d2b60550 100644
--- a/src/plugins/qmldesigner/designercore/imagecache/timestampprovider.h
+++ b/src/plugins/qmldesigner/designercore/imagecache/timestampprovider.h
@@ -33,6 +33,7 @@ class TimeStampProvider : public TimeStampProviderInterface
{
public:
Sqlite::TimeStamp timeStamp(Utils::SmallStringView name) const override;
+ Sqlite::TimeStamp pause() const override { return 0; }
};
} // namespace QmlDesigner
diff --git a/src/plugins/qmldesigner/designercore/imagecache/timestampproviderinterface.h b/src/plugins/qmldesigner/designercore/imagecache/timestampproviderinterface.h
index 33cffc9b49..4babac2796 100644
--- a/src/plugins/qmldesigner/designercore/imagecache/timestampproviderinterface.h
+++ b/src/plugins/qmldesigner/designercore/imagecache/timestampproviderinterface.h
@@ -36,6 +36,7 @@ class TimeStampProviderInterface
{
public:
virtual Sqlite::TimeStamp timeStamp(Utils::SmallStringView name) const = 0;
+ virtual Sqlite::TimeStamp pause() const = 0;
protected:
~TimeStampProviderInterface() = default;
diff --git a/src/plugins/qmldesigner/qmldesignerprojectmanager.cpp b/src/plugins/qmldesigner/qmldesignerprojectmanager.cpp
index 9ae83b5451..2d5359f86c 100644
--- a/src/plugins/qmldesigner/qmldesignerprojectmanager.cpp
+++ b/src/plugins/qmldesigner/qmldesignerprojectmanager.cpp
@@ -50,7 +50,7 @@
#include <imagecache/imagecacheconnectionmanager.h>
#include <imagecache/imagecachegenerator.h>
#include <imagecache/imagecachestorage.h>
-#include <imagecache/timestampprovider.h>
+#include <imagecache/timestampproviderinterface.h>
#include <coreplugin/icore.h>
@@ -70,6 +70,23 @@ QString defaultImagePath()
return qobject_cast<::QmlProjectManager::QmlBuildSystem *>(target->buildSystem());
}
+class TimeStampProvider : public TimeStampProviderInterface
+{
+public:
+ Sqlite::TimeStamp timeStamp(Utils::SmallStringView) const override
+ {
+ auto now = std::chrono::steady_clock::now();
+
+ return std::chrono::duration_cast<std::chrono::seconds>(now.time_since_epoch()).count();
+ }
+
+ Sqlite::TimeStamp pause() const override
+ {
+ using namespace std::chrono_literals;
+ return std::chrono::duration_cast<std::chrono::seconds>(1h).count();
+ }
+};
+
} // namespace
class PreviewImageCacheData
diff --git a/tests/unit/unittest/asynchronousimagefactory-test.cpp b/tests/unit/unittest/asynchronousimagefactory-test.cpp
index dfc40ceb5b..cc23374a57 100644
--- a/tests/unit/unittest/asynchronousimagefactory-test.cpp
+++ b/tests/unit/unittest/asynchronousimagefactory-test.cpp
@@ -109,14 +109,16 @@ TEST_F(AsynchronousImageFactory, RequestImageWithAuxiliaryDataRequestImageFromCo
notification.wait();
}
-TEST_F(AsynchronousImageFactory, DontRequestImageRequestImageFromCollectorIfFileWasNotUpdated)
+TEST_F(AsynchronousImageFactory, DontRequestImageRequestImageFromCollectorIfFileWasUpdatedRecently)
{
ON_CALL(storageMock, fetchModifiedImageTime(Eq("/path/to/Component.qml"))).WillByDefault([&](auto) {
notification.notify();
return Sqlite::TimeStamp{124};
});
ON_CALL(timeStampProviderMock, timeStamp(Eq("/path/to/Component.qml")))
- .WillByDefault(Return(Sqlite::TimeStamp{124}));
+ .WillByDefault(Return(Sqlite::TimeStamp{125}));
+ ON_CALL(timeStampProviderMock, timeStamp(Eq("/path/to/Component.qml")))
+ .WillByDefault(Return(Sqlite::TimeStamp{1}));
EXPECT_CALL(collectorMock, start(_, _, _, _, _)).Times(0);
@@ -124,6 +126,22 @@ TEST_F(AsynchronousImageFactory, DontRequestImageRequestImageFromCollectorIfFile
notification.wait();
}
+TEST_F(AsynchronousImageFactory, RequestImageRequestImageFromCollectorIfFileWasNotUpdatedRecently)
+{
+ ON_CALL(storageMock, fetchModifiedImageTime(Eq("/path/to/Component.qml")))
+ .WillByDefault(Return(Sqlite::TimeStamp{123}));
+ ON_CALL(timeStampProviderMock, timeStamp(Eq("/path/to/Component.qml")))
+ .WillByDefault(Return(Sqlite::TimeStamp{125}));
+ ON_CALL(timeStampProviderMock, pause()).WillByDefault(Return(Sqlite::TimeStamp{1}));
+
+ EXPECT_CALL(collectorMock, start(_, _, _, _, _)).WillOnce([&](auto, auto, auto, auto, auto) {
+ notification.notify();
+ });
+
+ factory.generate("/path/to/Component.qml");
+ notification.wait();
+}
+
TEST_F(AsynchronousImageFactory, CleanRemovesEntries)
{
EXPECT_CALL(collectorMock, start(Eq("/path/to/Component1.qml"), _, _, _, _))
@@ -153,4 +171,30 @@ TEST_F(AsynchronousImageFactory, AfterCleanNewJobsWorks)
notification.wait();
}
+TEST_F(AsynchronousImageFactory, CaptureImageCallbackStoresImage)
+{
+ ON_CALL(storageMock, fetchModifiedImageTime(Eq("/path/to/Component.qml")))
+ .WillByDefault(Return(Sqlite::TimeStamp{123}));
+ ON_CALL(timeStampProviderMock, timeStamp(Eq("/path/to/Component.qml")))
+ .WillByDefault(Return(Sqlite::TimeStamp{125}));
+ ON_CALL(timeStampProviderMock, pause()).WillByDefault(Return(Sqlite::TimeStamp{1}));
+ ON_CALL(collectorMock,
+ start(Eq("/path/to/Component.qml"),
+ Eq("id"),
+ VariantWith<Utils::monostate>(Utils::monostate{}),
+ _,
+ _))
+ .WillByDefault([&](auto, auto, auto, auto capture, auto) { capture(image1, smallImage1); });
+
+ EXPECT_CALL(storageMock,
+ storeImage(Eq("/path/to/Component.qml+id"),
+ Sqlite::TimeStamp{125},
+ Eq(image1),
+ Eq(smallImage1)))
+ .WillOnce([&](auto, auto, auto, auto) { notification.notify(); });
+
+ factory.generate("/path/to/Component.qml", "id");
+ notification.wait();
+}
+
} // namespace
diff --git a/tests/unit/unittest/mocktimestampprovider.h b/tests/unit/unittest/mocktimestampprovider.h
index 0adad4c030..39d58790f2 100644
--- a/tests/unit/unittest/mocktimestampprovider.h
+++ b/tests/unit/unittest/mocktimestampprovider.h
@@ -33,4 +33,5 @@ class MockTimeStampProvider : public QmlDesigner::TimeStampProviderInterface
{
public:
MOCK_METHOD(Sqlite::TimeStamp, timeStamp, (Utils::SmallStringView name), (const, override));
+ MOCK_METHOD(Sqlite::TimeStamp, pause, (), (const, override));
};