mirror of
https://github.com/simonbrunel/qtpromise.git
synced 2024-11-22 02:34:30 +08:00
Split QPromise tests per feature in separate .pro
This commit is contained in:
parent
36a0eed12a
commit
d3b69f1248
@ -1,7 +1,7 @@
|
|||||||
<a href="https://promisesaplus.com/" title="Promises/A+ 1.1"><img src="http://promisesaplus.com/assets/logo-small.png" alt="Promises/A+" align="right"/></a>
|
<a href="https://promisesaplus.com/" title="Promises/A+ 1.1"><img src="http://promisesaplus.com/assets/logo-small.png" alt="Promises/A+" align="right"/></a>
|
||||||
|
|
||||||
# QtPromise
|
# QtPromise
|
||||||
[![qpm](https://img.shields.io/github/release/simonbrunel/qtpromise.svg?style=flat-square&label=qpm&colorB=4CAF50)](http://www.qpm.io/packages/com.github.simonbrunel.qtpromise/index.html) [![Travis](https://img.shields.io/travis/simonbrunel/qtpromise.svg?style=flat-square)](https://travis-ci.org/simonbrunel/qtpromise) [![coverage](https://img.shields.io/codecov/c/github/simonbrunel/qtpromise.svg?style=flat-square)](https://codecov.io/gh/simonbrunel/qtpromise)
|
[![qpm](https://img.shields.io/github/release/simonbrunel/qtpromise.svg?style=flat-square&label=qpm&colorB=4CAF50)](http://www.qpm.io/packages/com.github.simonbrunel.qtpromise/index.html) [![Travis](https://img.shields.io/travis/simonbrunel/qtpromise/master.svg?style=flat-square)](https://travis-ci.org/simonbrunel/qtpromise) [![coverage](https://img.shields.io/codecov/c/github/simonbrunel/qtpromise.svg?style=flat-square)](https://codecov.io/gh/simonbrunel/qtpromise)
|
||||||
|
|
||||||
[Promises/A+](https://promisesaplus.com/) implementation for [Qt/C++](https://www.qt.io/).
|
[Promises/A+](https://promisesaplus.com/) implementation for [Qt/C++](https://www.qt.io/).
|
||||||
|
|
||||||
|
4
tests/auto/qtpromise/qpromise/construct/construct.pro
Normal file
4
tests/auto/qtpromise/qpromise/construct/construct.pro
Normal file
@ -0,0 +1,4 @@
|
|||||||
|
TARGET = tst_qpromise_construct
|
||||||
|
SOURCES += $$PWD/tst_construct.cpp
|
||||||
|
|
||||||
|
include(../../qtpromise.pri)
|
230
tests/auto/qtpromise/qpromise/construct/tst_construct.cpp
Normal file
230
tests/auto/qtpromise/qpromise/construct/tst_construct.cpp
Normal file
@ -0,0 +1,230 @@
|
|||||||
|
// Tests
|
||||||
|
#include "../../shared/utils.h"
|
||||||
|
|
||||||
|
// QtPromise
|
||||||
|
#include <QtPromise>
|
||||||
|
|
||||||
|
// Qt
|
||||||
|
#include <QtTest>
|
||||||
|
|
||||||
|
using namespace QtPromise;
|
||||||
|
|
||||||
|
class tst_qpromise_construct : public QObject
|
||||||
|
{
|
||||||
|
Q_OBJECT
|
||||||
|
|
||||||
|
private Q_SLOTS:
|
||||||
|
void resolveSyncOneArg();
|
||||||
|
void resolveSyncOneArg_void();
|
||||||
|
void resolveSyncTwoArgs();
|
||||||
|
void resolveSyncTwoArgs_void();
|
||||||
|
void resolveAsyncOneArg();
|
||||||
|
void resolveAsyncOneArg_void();
|
||||||
|
void resolveAsyncTwoArgs();
|
||||||
|
void resolveAsyncTwoArgs_void();
|
||||||
|
void rejectThrowOneArg();
|
||||||
|
void rejectThrowOneArg_void();
|
||||||
|
void rejectThrowTwoArgs();
|
||||||
|
void rejectThrowTwoArgs_void();
|
||||||
|
void rejectSync();
|
||||||
|
void rejectSync_void();
|
||||||
|
void rejectAsync();
|
||||||
|
void rejectAsync_void();
|
||||||
|
};
|
||||||
|
|
||||||
|
QTEST_MAIN(tst_qpromise_construct)
|
||||||
|
#include "tst_construct.moc"
|
||||||
|
|
||||||
|
void tst_qpromise_construct::resolveSyncOneArg()
|
||||||
|
{
|
||||||
|
QPromise<int> p([](const QPromiseResolve<int>& resolve) {
|
||||||
|
resolve(42);
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(p.isFulfilled(), true);
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString());
|
||||||
|
QCOMPARE(waitForValue(p, -1), 42);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_construct::resolveSyncOneArg_void()
|
||||||
|
{
|
||||||
|
QPromise<void> p([](const QPromiseResolve<void>& resolve) {
|
||||||
|
resolve();
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(p.isFulfilled(), true);
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString());
|
||||||
|
QCOMPARE(waitForValue(p, -1, 42), 42);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_construct::resolveSyncTwoArgs()
|
||||||
|
{
|
||||||
|
QPromise<int> p([](const QPromiseResolve<int>& resolve, const QPromiseReject<int>&) {
|
||||||
|
resolve(42);
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(p.isFulfilled(), true);
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString());
|
||||||
|
QCOMPARE(waitForValue(p, -1), 42);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_construct::resolveSyncTwoArgs_void()
|
||||||
|
{
|
||||||
|
QPromise<void> p([](const QPromiseResolve<void>& resolve, const QPromiseReject<void>&) {
|
||||||
|
resolve();
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(p.isFulfilled(), true);
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString());
|
||||||
|
QCOMPARE(waitForValue(p, -1, 42), 42);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_construct::resolveAsyncOneArg()
|
||||||
|
{
|
||||||
|
QPromise<int> p([](const QPromiseResolve<int>& resolve) {
|
||||||
|
QtPromisePrivate::qtpromise_defer([=]() {
|
||||||
|
resolve(42);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(p.isPending(), true);
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString());
|
||||||
|
QCOMPARE(waitForValue(p, -1), 42);
|
||||||
|
QCOMPARE(p.isFulfilled(), true);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_construct::resolveAsyncOneArg_void()
|
||||||
|
{
|
||||||
|
QPromise<void> p([](const QPromiseResolve<void>& resolve) {
|
||||||
|
QtPromisePrivate::qtpromise_defer([=]() {
|
||||||
|
resolve();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(p.isPending(), true);
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString());
|
||||||
|
QCOMPARE(waitForValue(p, -1, 42), 42);
|
||||||
|
QCOMPARE(p.isFulfilled(), true);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_construct::resolveAsyncTwoArgs()
|
||||||
|
{
|
||||||
|
QPromise<int> p([](const QPromiseResolve<int>& resolve, const QPromiseReject<int>&) {
|
||||||
|
QtPromisePrivate::qtpromise_defer([=]() {
|
||||||
|
resolve(42);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(p.isPending(), true);
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString());
|
||||||
|
QCOMPARE(waitForValue(p, -1), 42);
|
||||||
|
QCOMPARE(p.isFulfilled(), true);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_construct::resolveAsyncTwoArgs_void()
|
||||||
|
{
|
||||||
|
QPromise<void> p([](const QPromiseResolve<void>& resolve, const QPromiseReject<void>&) {
|
||||||
|
QtPromisePrivate::qtpromise_defer([=]() {
|
||||||
|
resolve();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(p.isPending(), true);
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString());
|
||||||
|
QCOMPARE(waitForValue(p, -1, 42), 42);
|
||||||
|
QCOMPARE(p.isFulfilled(), true);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_construct::rejectSync()
|
||||||
|
{
|
||||||
|
QPromise<int> p([](const QPromiseResolve<int>&, const QPromiseReject<int>& reject) {
|
||||||
|
reject(QString("foo"));
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
QCOMPARE(waitForValue(p, -1), -1);
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_construct::rejectSync_void()
|
||||||
|
{
|
||||||
|
QPromise<void> p([](const QPromiseResolve<void>&, const QPromiseReject<void>& reject) {
|
||||||
|
reject(QString("foo"));
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
QCOMPARE(waitForValue(p, -1, 42), -1);
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_construct::rejectAsync()
|
||||||
|
{
|
||||||
|
QPromise<int> p([](const QPromiseResolve<int>&, const QPromiseReject<int>& reject) {
|
||||||
|
QtPromisePrivate::qtpromise_defer([=]() {
|
||||||
|
reject(QString("foo"));
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(p.isPending(), true);
|
||||||
|
QCOMPARE(waitForValue(p, -1), -1);
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_construct::rejectAsync_void()
|
||||||
|
{
|
||||||
|
QPromise<void> p([](const QPromiseResolve<void>&, const QPromiseReject<void>& reject) {
|
||||||
|
QtPromisePrivate::qtpromise_defer([=]() {
|
||||||
|
reject(QString("foo"));
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(p.isPending(), true);
|
||||||
|
QCOMPARE(waitForValue(p, -1, 42), -1);
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_construct::rejectThrowOneArg()
|
||||||
|
{
|
||||||
|
QPromise<int> p([](const QPromiseResolve<int>&) {
|
||||||
|
throw QString("foo");
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
QCOMPARE(waitForValue(p, -1), -1);
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_construct::rejectThrowOneArg_void()
|
||||||
|
{
|
||||||
|
QPromise<void> p([](const QPromiseResolve<void>&) {
|
||||||
|
throw QString("foo");
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
QCOMPARE(waitForValue(p, -1, 42), -1);
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_construct::rejectThrowTwoArgs()
|
||||||
|
{
|
||||||
|
QPromise<int> p([](const QPromiseResolve<int>&, const QPromiseReject<int>&) {
|
||||||
|
throw QString("foo");
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
QCOMPARE(waitForValue(p, -1), -1);
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_construct::rejectThrowTwoArgs_void()
|
||||||
|
{
|
||||||
|
QPromise<void> p([](const QPromiseResolve<void>&, const QPromiseReject<void>&) {
|
||||||
|
throw QString("foo");
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
QCOMPARE(waitForValue(p, -1, 42), -1);
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
||||||
|
}
|
4
tests/auto/qtpromise/qpromise/delay/delay.pro
Normal file
4
tests/auto/qtpromise/qpromise/delay/delay.pro
Normal file
@ -0,0 +1,4 @@
|
|||||||
|
TARGET = tst_qpromise_delay
|
||||||
|
SOURCES += $$PWD/tst_delay.cpp
|
||||||
|
|
||||||
|
include(../../qtpromise.pri)
|
55
tests/auto/qtpromise/qpromise/delay/tst_delay.cpp
Normal file
55
tests/auto/qtpromise/qpromise/delay/tst_delay.cpp
Normal file
@ -0,0 +1,55 @@
|
|||||||
|
// Tests
|
||||||
|
#include "../../shared/utils.h"
|
||||||
|
|
||||||
|
// QtPromise
|
||||||
|
#include <QtPromise>
|
||||||
|
|
||||||
|
// Qt
|
||||||
|
#include <QtTest>
|
||||||
|
|
||||||
|
using namespace QtPromise;
|
||||||
|
|
||||||
|
class tst_qpromise_delay : public QObject
|
||||||
|
{
|
||||||
|
Q_OBJECT
|
||||||
|
|
||||||
|
private Q_SLOTS:
|
||||||
|
void fulfilled();
|
||||||
|
void rejected();
|
||||||
|
};
|
||||||
|
|
||||||
|
QTEST_MAIN(tst_qpromise_delay)
|
||||||
|
#include "tst_delay.moc"
|
||||||
|
|
||||||
|
void tst_qpromise_delay::fulfilled()
|
||||||
|
{
|
||||||
|
QElapsedTimer timer;
|
||||||
|
qint64 elapsed = -1;
|
||||||
|
|
||||||
|
timer.start();
|
||||||
|
|
||||||
|
auto p = QPromise<int>::resolve(42).delay(1000).finally([&]() {
|
||||||
|
elapsed = timer.elapsed();
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(waitForValue(p, -1), 42);
|
||||||
|
QCOMPARE(p.isFulfilled(), true);
|
||||||
|
QVERIFY(elapsed >= 1000 * 0.95); // Qt::CoarseTimer (default) Coarse timers try to
|
||||||
|
QVERIFY(elapsed <= 1000 * 1.05); // keep accuracy within 5% of the desired interval.
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_delay::rejected()
|
||||||
|
{
|
||||||
|
QElapsedTimer timer;
|
||||||
|
qint64 elapsed = -1;
|
||||||
|
|
||||||
|
timer.start();
|
||||||
|
|
||||||
|
auto p = QPromise<int>::reject(QString("foo")).delay(1000).finally([&]() {
|
||||||
|
elapsed = timer.elapsed();
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
QVERIFY(elapsed < 5);
|
||||||
|
}
|
4
tests/auto/qtpromise/qpromise/fail/fail.pro
Normal file
4
tests/auto/qtpromise/qpromise/fail/fail.pro
Normal file
@ -0,0 +1,4 @@
|
|||||||
|
TARGET = tst_qpromise_fail
|
||||||
|
SOURCES += $$PWD/tst_fail.cpp
|
||||||
|
|
||||||
|
include(../../qtpromise.pri)
|
83
tests/auto/qtpromise/qpromise/fail/tst_fail.cpp
Normal file
83
tests/auto/qtpromise/qpromise/fail/tst_fail.cpp
Normal file
@ -0,0 +1,83 @@
|
|||||||
|
// Tests
|
||||||
|
#include "../../shared/utils.h"
|
||||||
|
|
||||||
|
// QtPromise
|
||||||
|
#include <QtPromise>
|
||||||
|
|
||||||
|
// Qt
|
||||||
|
#include <QtTest>
|
||||||
|
|
||||||
|
using namespace QtPromise;
|
||||||
|
|
||||||
|
class tst_qpromise_fail : public QObject
|
||||||
|
{
|
||||||
|
Q_OBJECT
|
||||||
|
|
||||||
|
private Q_SLOTS:
|
||||||
|
void sameType();
|
||||||
|
void baseClass();
|
||||||
|
void catchAll();
|
||||||
|
// TODO: sync / async
|
||||||
|
};
|
||||||
|
|
||||||
|
QTEST_MAIN(tst_qpromise_fail)
|
||||||
|
#include "tst_fail.moc"
|
||||||
|
|
||||||
|
void tst_qpromise_fail::sameType()
|
||||||
|
{
|
||||||
|
// http://en.cppreference.com/w/cpp/error/exception
|
||||||
|
auto p = QPromise<int>::reject(std::out_of_range("foo"));
|
||||||
|
|
||||||
|
QString error;
|
||||||
|
p.fail([&](const std::domain_error& e) {
|
||||||
|
error += QString(e.what()) + "0";
|
||||||
|
return -1;
|
||||||
|
}).fail([&](const std::out_of_range& e) {
|
||||||
|
error += QString(e.what()) + "1";
|
||||||
|
return -1;
|
||||||
|
}).fail([&](const std::exception& e) {
|
||||||
|
error += QString(e.what()) + "2";
|
||||||
|
return -1;
|
||||||
|
}).wait();
|
||||||
|
|
||||||
|
QCOMPARE(error, QString("foo1"));
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_fail::baseClass()
|
||||||
|
{
|
||||||
|
// http://en.cppreference.com/w/cpp/error/exception
|
||||||
|
auto p = QPromise<int>::reject(std::out_of_range("foo"));
|
||||||
|
|
||||||
|
QString error;
|
||||||
|
p.fail([&](const std::runtime_error& e) {
|
||||||
|
error += QString(e.what()) + "0";
|
||||||
|
return -1;
|
||||||
|
}).fail([&](const std::logic_error& e) {
|
||||||
|
error += QString(e.what()) + "1";
|
||||||
|
return -1;
|
||||||
|
}).fail([&](const std::exception& e) {
|
||||||
|
error += QString(e.what()) + "2";
|
||||||
|
return -1;
|
||||||
|
}).wait();
|
||||||
|
|
||||||
|
QCOMPARE(error, QString("foo1"));
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_fail::catchAll()
|
||||||
|
{
|
||||||
|
auto p = QPromise<int>::reject(std::out_of_range("foo"));
|
||||||
|
|
||||||
|
QString error;
|
||||||
|
p.fail([&](const std::runtime_error& e) {
|
||||||
|
error += QString(e.what()) + "0";
|
||||||
|
return -1;
|
||||||
|
}).fail([&]() {
|
||||||
|
error += "bar";
|
||||||
|
return -1;
|
||||||
|
}).fail([&](const std::exception& e) {
|
||||||
|
error += QString(e.what()) + "2";
|
||||||
|
return -1;
|
||||||
|
}).wait();
|
||||||
|
|
||||||
|
QCOMPARE(error, QString("bar"));
|
||||||
|
}
|
4
tests/auto/qtpromise/qpromise/finally/finally.pro
Normal file
4
tests/auto/qtpromise/qpromise/finally/finally.pro
Normal file
@ -0,0 +1,4 @@
|
|||||||
|
TARGET = tst_qpromise_finally
|
||||||
|
SOURCES += $$PWD/tst_finally.cpp
|
||||||
|
|
||||||
|
include(../../qtpromise.pri)
|
204
tests/auto/qtpromise/qpromise/finally/tst_finally.cpp
Normal file
204
tests/auto/qtpromise/qpromise/finally/tst_finally.cpp
Normal file
@ -0,0 +1,204 @@
|
|||||||
|
// Tests
|
||||||
|
#include "../../shared/utils.h"
|
||||||
|
|
||||||
|
// QtPromise
|
||||||
|
#include <QtPromise>
|
||||||
|
|
||||||
|
// Qt
|
||||||
|
#include <QtTest>
|
||||||
|
|
||||||
|
using namespace QtPromise;
|
||||||
|
|
||||||
|
class tst_qpromise_finally : public QObject
|
||||||
|
{
|
||||||
|
Q_OBJECT
|
||||||
|
|
||||||
|
private Q_SLOTS:
|
||||||
|
void fulfilledSync();
|
||||||
|
void fulfilledSync_void();
|
||||||
|
void fulfilledThrows();
|
||||||
|
void fulfilledThrows_void();
|
||||||
|
void fulfilledAsyncResolve();
|
||||||
|
void fulfilledAsyncReject();
|
||||||
|
void rejectedSync();
|
||||||
|
void rejectedSync_void();
|
||||||
|
void rejectedThrows();
|
||||||
|
void rejectedThrows_void();
|
||||||
|
void rejectedAsyncResolve();
|
||||||
|
void rejectedAsyncReject();
|
||||||
|
};
|
||||||
|
|
||||||
|
QTEST_MAIN(tst_qpromise_finally)
|
||||||
|
#include "tst_finally.moc"
|
||||||
|
|
||||||
|
void tst_qpromise_finally::fulfilledSync()
|
||||||
|
{
|
||||||
|
int value = -1;
|
||||||
|
auto p = QPromise<int>::resolve(42).finally([&]() {
|
||||||
|
value = 8;
|
||||||
|
return 16; // ignored!
|
||||||
|
});
|
||||||
|
|
||||||
|
Q_STATIC_ASSERT((std::is_same<decltype(p), QPromise<int> >::value));
|
||||||
|
QCOMPARE(waitForValue(p, -1), 42);
|
||||||
|
QCOMPARE(p.isFulfilled(), true);
|
||||||
|
QCOMPARE(value, 8);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_finally::fulfilledSync_void()
|
||||||
|
{
|
||||||
|
int value = -1;
|
||||||
|
auto p = QPromise<void>::resolve().finally([&]() {
|
||||||
|
value = 8;
|
||||||
|
return 16; // ignored!
|
||||||
|
});
|
||||||
|
|
||||||
|
Q_STATIC_ASSERT((std::is_same<decltype(p), QPromise<void> >::value));
|
||||||
|
QCOMPARE(waitForValue(p, -1, 42), 42);
|
||||||
|
QCOMPARE(p.isFulfilled(), true);
|
||||||
|
QCOMPARE(value, 8);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_finally::fulfilledThrows()
|
||||||
|
{
|
||||||
|
auto p = QPromise<int>::resolve(42).finally([&]() {
|
||||||
|
throw QString("bar");
|
||||||
|
});
|
||||||
|
|
||||||
|
Q_STATIC_ASSERT((std::is_same<decltype(p), QPromise<int> >::value));
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString("bar"));
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_finally::fulfilledThrows_void()
|
||||||
|
{
|
||||||
|
auto p = QPromise<void>::resolve().finally([&]() {
|
||||||
|
throw QString("bar");
|
||||||
|
});
|
||||||
|
|
||||||
|
Q_STATIC_ASSERT((std::is_same<decltype(p), QPromise<void> >::value));
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString("bar"));
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_finally::fulfilledAsyncResolve()
|
||||||
|
{
|
||||||
|
QVector<int> values;
|
||||||
|
auto p = QPromise<int>::resolve(42).finally([&]() {
|
||||||
|
QPromise<int> p([&](const QPromiseResolve<int>& resolve) {
|
||||||
|
QtPromisePrivate::qtpromise_defer([=, &values]() {
|
||||||
|
values << 64;
|
||||||
|
resolve(16); // ignored!
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
values << 8;
|
||||||
|
return p;
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(waitForValue(p, -1), 42);
|
||||||
|
QCOMPARE(p.isFulfilled(), true);
|
||||||
|
QCOMPARE(values, QVector<int>({8, 64}));
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_finally::fulfilledAsyncReject()
|
||||||
|
{
|
||||||
|
auto p = QPromise<int>::resolve(42).finally([]() {
|
||||||
|
return QPromise<int>([](const QPromiseResolve<int>&, const QPromiseReject<int>& reject) {
|
||||||
|
QtPromisePrivate::qtpromise_defer([=]() {
|
||||||
|
reject(QString("bar"));
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString("bar"));
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_finally::rejectedSync()
|
||||||
|
{
|
||||||
|
int value = -1;
|
||||||
|
auto p = QPromise<int>::reject(QString("foo")).finally([&]() {
|
||||||
|
value = 8;
|
||||||
|
return 16; // ignored!
|
||||||
|
});
|
||||||
|
|
||||||
|
Q_STATIC_ASSERT((std::is_same<decltype(p), QPromise<int> >::value));
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
QCOMPARE(value, 8);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_finally::rejectedSync_void()
|
||||||
|
{
|
||||||
|
int value = -1;
|
||||||
|
auto p = QPromise<void>::reject(QString("foo")).finally([&]() {
|
||||||
|
value = 8;
|
||||||
|
return 16; // ignored!
|
||||||
|
});
|
||||||
|
|
||||||
|
Q_STATIC_ASSERT((std::is_same<decltype(p), QPromise<void> >::value));
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
QCOMPARE(value, 8);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_finally::rejectedThrows()
|
||||||
|
{
|
||||||
|
auto p = QPromise<int>::reject(QString("foo")).finally([&]() {
|
||||||
|
throw QString("bar");
|
||||||
|
});
|
||||||
|
|
||||||
|
Q_STATIC_ASSERT((std::is_same<decltype(p), QPromise<int> >::value));
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString("bar"));
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_finally::rejectedThrows_void()
|
||||||
|
{
|
||||||
|
auto p = QPromise<void>::reject(QString("foo")).finally([&]() {
|
||||||
|
throw QString("bar");
|
||||||
|
});
|
||||||
|
|
||||||
|
Q_STATIC_ASSERT((std::is_same<decltype(p), QPromise<void> >::value));
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString("bar"));
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_finally::rejectedAsyncResolve()
|
||||||
|
{
|
||||||
|
QVector<int> values;
|
||||||
|
auto p = QPromise<int>::reject(QString("foo")).finally([&]() {
|
||||||
|
QPromise<int> p([&](const QPromiseResolve<int>& resolve) {
|
||||||
|
QtPromisePrivate::qtpromise_defer([=, &values]() {
|
||||||
|
values << 64;
|
||||||
|
resolve(16); // ignored!
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
values << 8;
|
||||||
|
return p;
|
||||||
|
});
|
||||||
|
|
||||||
|
p.then([&](int r) {
|
||||||
|
values << r;
|
||||||
|
}).wait();
|
||||||
|
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
QCOMPARE(values, QVector<int>({8, 64}));
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_finally::rejectedAsyncReject()
|
||||||
|
{
|
||||||
|
auto p = QPromise<int>::reject(QString("foo")).finally([]() {
|
||||||
|
return QPromise<int>([](const QPromiseResolve<int>&, const QPromiseReject<int>& reject) {
|
||||||
|
QtPromisePrivate::qtpromise_defer([=]() {
|
||||||
|
reject(QString("bar"));
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString("bar"));
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
}
|
@ -1,4 +1,9 @@
|
|||||||
TARGET = tst_qpromise
|
TEMPLATE = subdirs
|
||||||
SOURCES += $$PWD/tst_qpromise.cpp
|
SUBDIRS += \
|
||||||
|
construct \
|
||||||
include(../qtpromise.pri)
|
delay \
|
||||||
|
fail \
|
||||||
|
finally \
|
||||||
|
tap \
|
||||||
|
then \
|
||||||
|
timeout
|
||||||
|
4
tests/auto/qtpromise/qpromise/tap/tap.pro
Normal file
4
tests/auto/qtpromise/qpromise/tap/tap.pro
Normal file
@ -0,0 +1,4 @@
|
|||||||
|
TARGET = tst_qpromise_tap
|
||||||
|
SOURCES += $$PWD/tst_tap.cpp
|
||||||
|
|
||||||
|
include(../../qtpromise.pri)
|
145
tests/auto/qtpromise/qpromise/tap/tst_tap.cpp
Normal file
145
tests/auto/qtpromise/qpromise/tap/tst_tap.cpp
Normal file
@ -0,0 +1,145 @@
|
|||||||
|
// Tests
|
||||||
|
#include "../../shared/utils.h"
|
||||||
|
|
||||||
|
// QtPromise
|
||||||
|
#include <QtPromise>
|
||||||
|
|
||||||
|
// Qt
|
||||||
|
#include <QtTest>
|
||||||
|
|
||||||
|
using namespace QtPromise;
|
||||||
|
|
||||||
|
class tst_qpromise_tap : public QObject
|
||||||
|
{
|
||||||
|
Q_OBJECT
|
||||||
|
|
||||||
|
private Q_SLOTS:
|
||||||
|
void fulfilledSync();
|
||||||
|
void fulfilledSync_void();
|
||||||
|
void fulfilledThrows();
|
||||||
|
void fulfilledThrows_void();
|
||||||
|
void fulfilledAsyncResolve();
|
||||||
|
void fulfilledAsyncReject();
|
||||||
|
void rejectedSync();
|
||||||
|
void rejectedSync_void();
|
||||||
|
};
|
||||||
|
|
||||||
|
QTEST_MAIN(tst_qpromise_tap)
|
||||||
|
#include "tst_tap.moc"
|
||||||
|
|
||||||
|
void tst_qpromise_tap::fulfilledSync()
|
||||||
|
{
|
||||||
|
int value = -1;
|
||||||
|
auto p = QPromise<int>::resolve(42).tap([&](int res) {
|
||||||
|
value = res + 1;
|
||||||
|
return 8;
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(waitForValue(p, 42), 42);
|
||||||
|
QCOMPARE(p.isFulfilled(), true);
|
||||||
|
QCOMPARE(value, 43);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_tap::fulfilledSync_void()
|
||||||
|
{
|
||||||
|
int value = -1;
|
||||||
|
auto p = QPromise<void>::resolve().tap([&]() {
|
||||||
|
value = 43;
|
||||||
|
return 8;
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(waitForValue(p, -1, 42), 42);
|
||||||
|
QCOMPARE(p.isFulfilled(), true);
|
||||||
|
QCOMPARE(value, 43);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_tap::fulfilledThrows()
|
||||||
|
{
|
||||||
|
auto p = QPromise<int>::resolve(42).tap([&](int) {
|
||||||
|
throw QString("foo");
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_tap::fulfilledThrows_void()
|
||||||
|
{
|
||||||
|
auto p = QPromise<void>::resolve().tap([&]() {
|
||||||
|
throw QString("foo");
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_tap::fulfilledAsyncResolve()
|
||||||
|
{
|
||||||
|
QVector<int> values;
|
||||||
|
auto p = QPromise<int>::resolve(1).tap([&](int) {
|
||||||
|
QPromise<int> p([&](const QPromiseResolve<int>& resolve) {
|
||||||
|
QtPromisePrivate::qtpromise_defer([=, &values]() {
|
||||||
|
values << 3;
|
||||||
|
resolve(4); // ignored!
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
values << 2;
|
||||||
|
return p;
|
||||||
|
});
|
||||||
|
|
||||||
|
p.then([&](int r) {
|
||||||
|
values << r;
|
||||||
|
}).wait();
|
||||||
|
|
||||||
|
QCOMPARE(p.isFulfilled(), true);
|
||||||
|
QCOMPARE(values, QVector<int>({2, 3, 1}));
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_tap::fulfilledAsyncReject()
|
||||||
|
{
|
||||||
|
QVector<int> values;
|
||||||
|
auto p = QPromise<int>::resolve(1).tap([&](int) {
|
||||||
|
QPromise<int> p([&](const QPromiseResolve<int>&, const QPromiseReject<int>& reject) {
|
||||||
|
QtPromisePrivate::qtpromise_defer([=, &values]() {
|
||||||
|
values << 3;
|
||||||
|
reject(QString("foo"));
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
values << 2;
|
||||||
|
return p;
|
||||||
|
});
|
||||||
|
|
||||||
|
p.then([&](int r) {
|
||||||
|
values << r;
|
||||||
|
}).wait();
|
||||||
|
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
QCOMPARE(values, QVector<int>({2, 3}));
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_tap::rejectedSync()
|
||||||
|
{
|
||||||
|
int value = -1;
|
||||||
|
auto p = QPromise<int>::reject(QString("foo")).tap([&](int res) {
|
||||||
|
value = res + 1;
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
QCOMPARE(value, -1);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_tap::rejectedSync_void()
|
||||||
|
{
|
||||||
|
int value = -1;
|
||||||
|
auto p = QPromise<void>::reject(QString("foo")).tap([&]() {
|
||||||
|
value = 43;
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
QCOMPARE(value, -1);
|
||||||
|
}
|
4
tests/auto/qtpromise/qpromise/then/then.pro
Normal file
4
tests/auto/qtpromise/qpromise/then/then.pro
Normal file
@ -0,0 +1,4 @@
|
|||||||
|
TARGET = tst_qpromise_then
|
||||||
|
SOURCES += $$PWD/tst_then.cpp
|
||||||
|
|
||||||
|
include(../../qtpromise.pri)
|
126
tests/auto/qtpromise/qpromise/then/tst_then.cpp
Normal file
126
tests/auto/qtpromise/qpromise/then/tst_then.cpp
Normal file
@ -0,0 +1,126 @@
|
|||||||
|
// Tests
|
||||||
|
#include "../../shared/utils.h"
|
||||||
|
|
||||||
|
// QtPromise
|
||||||
|
#include <QtPromise>
|
||||||
|
|
||||||
|
// Qt
|
||||||
|
#include <QtTest>
|
||||||
|
|
||||||
|
using namespace QtPromise;
|
||||||
|
|
||||||
|
class tst_qpromise_then : public QObject
|
||||||
|
{
|
||||||
|
Q_OBJECT
|
||||||
|
|
||||||
|
private Q_SLOTS:
|
||||||
|
void resolveSync();
|
||||||
|
void resolveAsync();
|
||||||
|
void rejectSync();
|
||||||
|
void rejectAsync();
|
||||||
|
void skipResult();
|
||||||
|
void noHandler();
|
||||||
|
};
|
||||||
|
|
||||||
|
QTEST_MAIN(tst_qpromise_then)
|
||||||
|
#include "tst_then.moc"
|
||||||
|
|
||||||
|
void tst_qpromise_then::resolveSync()
|
||||||
|
{
|
||||||
|
QVariantList values;
|
||||||
|
|
||||||
|
auto input = QPromise<int>::resolve(42);
|
||||||
|
auto output = input.then([&](int res) {
|
||||||
|
values << res;
|
||||||
|
return QString::number(res+1);
|
||||||
|
});
|
||||||
|
|
||||||
|
output.then([&](const QString& res) {
|
||||||
|
values << res;
|
||||||
|
}).then([&]() {
|
||||||
|
values << 44;
|
||||||
|
}).wait();
|
||||||
|
|
||||||
|
QCOMPARE(values, QVariantList({42, QString("43"), 44}));
|
||||||
|
QCOMPARE(input.isFulfilled(), true);
|
||||||
|
QCOMPARE(output.isFulfilled(), true);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_then::resolveAsync()
|
||||||
|
{
|
||||||
|
auto p = QPromise<int>::resolve(42).then([](int res) {
|
||||||
|
return QPromise<QString>([=](const QPromiseResolve<QString>& resolve) {
|
||||||
|
QtPromisePrivate::qtpromise_defer([=]() {
|
||||||
|
resolve(QString("foo%1").arg(res));
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
Q_STATIC_ASSERT((std::is_same<decltype(p), QPromise<QString> >::value));
|
||||||
|
QCOMPARE(waitForValue(p, QString()), QString("foo42"));
|
||||||
|
QCOMPARE(p.isFulfilled(), true);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_then::rejectSync()
|
||||||
|
{
|
||||||
|
auto input = QPromise<int>::resolve(42);
|
||||||
|
auto output = input.then([](int res) {
|
||||||
|
throw QString("foo%1").arg(res);
|
||||||
|
return 42;
|
||||||
|
});
|
||||||
|
|
||||||
|
QString error;
|
||||||
|
output.then([&](int res) {
|
||||||
|
error += "bar" + QString::number(res);
|
||||||
|
}).fail([&](const QString& err) {
|
||||||
|
error += err;
|
||||||
|
}).wait();
|
||||||
|
|
||||||
|
QCOMPARE(error, QString("foo42"));
|
||||||
|
QCOMPARE(input.isFulfilled(), true);
|
||||||
|
QCOMPARE(output.isRejected(), true);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_then::rejectAsync()
|
||||||
|
{
|
||||||
|
auto p = QPromise<int>::resolve(42).then([](int res) {
|
||||||
|
return QPromise<void>([=](const QPromiseResolve<void>&, const QPromiseReject<void>& reject) {
|
||||||
|
QtPromisePrivate::qtpromise_defer([=]() {
|
||||||
|
reject(QString("foo%1").arg(res));
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
Q_STATIC_ASSERT((std::is_same<decltype(p), QPromise<void> >::value));
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString("foo42"));
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_then::skipResult()
|
||||||
|
{
|
||||||
|
auto p = QPromise<int>::resolve(42);
|
||||||
|
|
||||||
|
int value = -1;
|
||||||
|
p.then([&]() {
|
||||||
|
value = 43;
|
||||||
|
}).wait();
|
||||||
|
|
||||||
|
Q_STATIC_ASSERT((std::is_same<decltype(p), QPromise<int> >::value));
|
||||||
|
QCOMPARE(value, 43);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_then::noHandler()
|
||||||
|
{
|
||||||
|
{ // resolved
|
||||||
|
auto p = QPromise<int>::resolve(42).then(nullptr);
|
||||||
|
|
||||||
|
QCOMPARE(waitForValue(p, -1), 42);
|
||||||
|
QCOMPARE(p.isFulfilled(), true);
|
||||||
|
}
|
||||||
|
{ // rejected
|
||||||
|
auto p = QPromise<int>::reject(QString("foo")).then(nullptr);
|
||||||
|
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
}
|
||||||
|
}
|
4
tests/auto/qtpromise/qpromise/timeout/timeout.pro
Normal file
4
tests/auto/qtpromise/qpromise/timeout/timeout.pro
Normal file
@ -0,0 +1,4 @@
|
|||||||
|
TARGET = tst_qpromise_timeout
|
||||||
|
SOURCES += $$PWD/tst_timeout.cpp
|
||||||
|
|
||||||
|
include(../../qtpromise.pri)
|
92
tests/auto/qtpromise/qpromise/timeout/tst_timeout.cpp
Normal file
92
tests/auto/qtpromise/qpromise/timeout/tst_timeout.cpp
Normal file
@ -0,0 +1,92 @@
|
|||||||
|
// Tests
|
||||||
|
#include "../../shared/utils.h"
|
||||||
|
|
||||||
|
// QtPromise
|
||||||
|
#include <QtPromise>
|
||||||
|
|
||||||
|
// Qt
|
||||||
|
#include <QtTest>
|
||||||
|
|
||||||
|
using namespace QtPromise;
|
||||||
|
|
||||||
|
class tst_qpromise_timeout : public QObject
|
||||||
|
{
|
||||||
|
Q_OBJECT
|
||||||
|
|
||||||
|
private Q_SLOTS:
|
||||||
|
void fulfilled();
|
||||||
|
void rejected();
|
||||||
|
void timeout();
|
||||||
|
};
|
||||||
|
|
||||||
|
QTEST_MAIN(tst_qpromise_timeout)
|
||||||
|
#include "tst_timeout.moc"
|
||||||
|
|
||||||
|
void tst_qpromise_timeout::fulfilled()
|
||||||
|
{
|
||||||
|
QElapsedTimer timer;
|
||||||
|
qint64 elapsed = -1;
|
||||||
|
|
||||||
|
timer.start();
|
||||||
|
|
||||||
|
auto p = QPromise<int>([](const QPromiseResolve<int>& resolve) {
|
||||||
|
QTimer::singleShot(1000, [=]() {
|
||||||
|
resolve(42);
|
||||||
|
});
|
||||||
|
}).timeout(2000).finally([&]() {
|
||||||
|
elapsed = timer.elapsed();
|
||||||
|
});
|
||||||
|
|
||||||
|
QCOMPARE(waitForValue(p, -1), 42);
|
||||||
|
QCOMPARE(p.isFulfilled(), true);
|
||||||
|
QVERIFY(elapsed < 2000);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_timeout::rejected()
|
||||||
|
{
|
||||||
|
QElapsedTimer timer;
|
||||||
|
qint64 elapsed = -1;
|
||||||
|
|
||||||
|
timer.start();
|
||||||
|
|
||||||
|
auto p = QPromise<int>([](const QPromiseResolve<int>&, const QPromiseReject<int>& reject) {
|
||||||
|
QTimer::singleShot(1000, [=]() {
|
||||||
|
reject(QString("foo"));
|
||||||
|
});
|
||||||
|
}).timeout(2000).finally([&]() {
|
||||||
|
elapsed = timer.elapsed();
|
||||||
|
});
|
||||||
|
|
||||||
|
|
||||||
|
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
QVERIFY(elapsed < 2000);
|
||||||
|
}
|
||||||
|
|
||||||
|
void tst_qpromise_timeout::timeout()
|
||||||
|
{
|
||||||
|
QElapsedTimer timer;
|
||||||
|
qint64 elapsed = -1;
|
||||||
|
bool failed = false;
|
||||||
|
|
||||||
|
timer.start();
|
||||||
|
|
||||||
|
auto p = QPromise<int>([](const QPromiseResolve<int>& resolve) {
|
||||||
|
QTimer::singleShot(4000, [=]() {
|
||||||
|
resolve(42);
|
||||||
|
});
|
||||||
|
}).timeout(2000).finally([&]() {
|
||||||
|
elapsed = timer.elapsed();
|
||||||
|
});
|
||||||
|
|
||||||
|
p.fail([&](const QPromiseTimeoutException&) {
|
||||||
|
failed = true;
|
||||||
|
return -1;
|
||||||
|
}).wait();
|
||||||
|
|
||||||
|
QCOMPARE(waitForValue(p, -1), -1);
|
||||||
|
QCOMPARE(p.isRejected(), true);
|
||||||
|
QCOMPARE(failed, true);
|
||||||
|
QVERIFY(elapsed >= 2000 * 0.95); // Qt::CoarseTimer (default) Coarse timers try to
|
||||||
|
QVERIFY(elapsed <= 2000 * 1.05); // keep accuracy within 5% of the desired interval.
|
||||||
|
}
|
@ -1,766 +0,0 @@
|
|||||||
// QtPromise
|
|
||||||
#include <QtPromise>
|
|
||||||
|
|
||||||
// Qt
|
|
||||||
#include <QtTest>
|
|
||||||
#include <QElapsedTimer>
|
|
||||||
|
|
||||||
using namespace QtPromise;
|
|
||||||
using namespace QtPromisePrivate;
|
|
||||||
|
|
||||||
class tst_qpromise : public QObject
|
|
||||||
{
|
|
||||||
Q_OBJECT
|
|
||||||
|
|
||||||
private Q_SLOTS:
|
|
||||||
void resolveSync();
|
|
||||||
void resolveSync_void();
|
|
||||||
void resolveDelayed();
|
|
||||||
void rejectSync();
|
|
||||||
void rejectDelayed();
|
|
||||||
void rejectThrows();
|
|
||||||
|
|
||||||
void thenReturns();
|
|
||||||
void thenThrows();
|
|
||||||
void thenNullPtr();
|
|
||||||
void thenSkipResult();
|
|
||||||
void thenDelayedResolved();
|
|
||||||
void thenDelayedRejected();
|
|
||||||
|
|
||||||
void failSameType();
|
|
||||||
void failBaseClass();
|
|
||||||
void failCatchAll();
|
|
||||||
|
|
||||||
void finallyFulfilled();
|
|
||||||
void finallyFulfilled_void();
|
|
||||||
void finallyRejected();
|
|
||||||
void finallyRejected_void();
|
|
||||||
void finallyThrows();
|
|
||||||
void finallyThrows_void();
|
|
||||||
void finallyDelayedResolved();
|
|
||||||
void finallyDelayedRejected();
|
|
||||||
|
|
||||||
void tapFulfilled();
|
|
||||||
void tapFulfilled_void();
|
|
||||||
void tapRejected();
|
|
||||||
void tapRejected_void();
|
|
||||||
void tapThrows();
|
|
||||||
void tapThrows_void();
|
|
||||||
void tapDelayedResolved();
|
|
||||||
void tapDelayedRejected();
|
|
||||||
|
|
||||||
void timeoutFulfilled();
|
|
||||||
void timeoutRejected();
|
|
||||||
void timeoutReject();
|
|
||||||
|
|
||||||
void delayFulfilled();
|
|
||||||
void delayRejected();
|
|
||||||
|
|
||||||
}; // class tst_qpromise
|
|
||||||
|
|
||||||
QTEST_MAIN(tst_qpromise)
|
|
||||||
#include "tst_qpromise.moc"
|
|
||||||
|
|
||||||
template <typename T>
|
|
||||||
T waitForValue(const QPromise<T>& promise, const T& initial)
|
|
||||||
{
|
|
||||||
T value(initial);
|
|
||||||
promise.then([&](const T& res) {
|
|
||||||
value = res;
|
|
||||||
}).wait();
|
|
||||||
return value;
|
|
||||||
}
|
|
||||||
|
|
||||||
template <typename T>
|
|
||||||
T waitForValue(const QPromise<void>& promise, const T& initial, const T& expected)
|
|
||||||
{
|
|
||||||
T value(initial);
|
|
||||||
promise.then([&]() {
|
|
||||||
value = expected;
|
|
||||||
}).wait();
|
|
||||||
return value;
|
|
||||||
}
|
|
||||||
|
|
||||||
template <typename T, typename E>
|
|
||||||
E waitForError(const QPromise<T>& promise, const E& initial)
|
|
||||||
{
|
|
||||||
E error(initial);
|
|
||||||
promise.fail([&](const E& err) {
|
|
||||||
error = err;
|
|
||||||
return T();
|
|
||||||
}).wait();
|
|
||||||
return error;
|
|
||||||
}
|
|
||||||
|
|
||||||
template <typename E>
|
|
||||||
E waitForError(const QPromise<void>& promise, const E& initial)
|
|
||||||
{
|
|
||||||
E error(initial);
|
|
||||||
promise.fail([&](const E& err) {
|
|
||||||
error = err;
|
|
||||||
}).wait();
|
|
||||||
return error;
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::resolveSync()
|
|
||||||
{
|
|
||||||
{ // resolver(resolve)
|
|
||||||
QPromise<int> p([](const QPromiseResolve<int>& resolve) {
|
|
||||||
resolve(42);
|
|
||||||
});
|
|
||||||
|
|
||||||
QCOMPARE(p.isFulfilled(), true);
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString());
|
|
||||||
QCOMPARE(waitForValue(p, -1), 42);
|
|
||||||
}
|
|
||||||
{ // resolver(resolve, reject)
|
|
||||||
QPromise<int> p([](const QPromiseResolve<int>& resolve, const QPromiseReject<int>&) {
|
|
||||||
resolve(42);
|
|
||||||
});
|
|
||||||
|
|
||||||
QCOMPARE(p.isFulfilled(), true);
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString());
|
|
||||||
QCOMPARE(waitForValue(p, -1), 42);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::resolveSync_void()
|
|
||||||
{
|
|
||||||
{ // resolver(resolve)
|
|
||||||
QPromise<void> p([](const QPromiseResolve<void>& resolve) {
|
|
||||||
resolve();
|
|
||||||
});
|
|
||||||
|
|
||||||
QCOMPARE(p.isFulfilled(), true);
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString());
|
|
||||||
QCOMPARE(waitForValue(p, -1, 42), 42);
|
|
||||||
}
|
|
||||||
{ // resolver(resolve, reject)
|
|
||||||
QPromise<void> p([](const QPromiseResolve<void>& resolve, const QPromiseReject<void>&) {
|
|
||||||
resolve();
|
|
||||||
});
|
|
||||||
|
|
||||||
QCOMPARE(p.isFulfilled(), true);
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString());
|
|
||||||
QCOMPARE(waitForValue(p, -1, 42), 42);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::resolveDelayed()
|
|
||||||
{
|
|
||||||
{ // resolver(resolve)
|
|
||||||
QPromise<int> p([](const QPromiseResolve<int>& resolve) {
|
|
||||||
QtPromisePrivate::qtpromise_defer([=]() {
|
|
||||||
resolve(42);
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
QCOMPARE(p.isPending(), true);
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString());
|
|
||||||
QCOMPARE(waitForValue(p, -1), 42);
|
|
||||||
QCOMPARE(p.isFulfilled(), true);
|
|
||||||
}
|
|
||||||
{ // resolver(resolve, reject)
|
|
||||||
QPromise<int> p([](const QPromiseResolve<int>& resolve, const QPromiseReject<int>&) {
|
|
||||||
QtPromisePrivate::qtpromise_defer([=]() {
|
|
||||||
resolve(42);
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
QCOMPARE(p.isPending(), true);
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString());
|
|
||||||
QCOMPARE(waitForValue(p, -1), 42);
|
|
||||||
QCOMPARE(p.isFulfilled(), true);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::rejectSync()
|
|
||||||
{
|
|
||||||
QPromise<int> p([](const QPromiseResolve<int>&, const QPromiseReject<int>& reject) {
|
|
||||||
reject(QString("foo"));
|
|
||||||
});
|
|
||||||
|
|
||||||
QCOMPARE(p.isRejected(), true);
|
|
||||||
QCOMPARE(waitForValue(p, -1), -1);
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::rejectDelayed()
|
|
||||||
{
|
|
||||||
QPromise<int> p([](const QPromiseResolve<int>&, const QPromiseReject<int>& reject) {
|
|
||||||
QtPromisePrivate::qtpromise_defer([=]() {
|
|
||||||
reject(QString("foo"));
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
QCOMPARE(p.isPending(), true);
|
|
||||||
QCOMPARE(waitForValue(p, -1), -1);
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
|
||||||
QCOMPARE(p.isRejected(), true);
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::rejectThrows()
|
|
||||||
{
|
|
||||||
{ // resolver(resolve)
|
|
||||||
QPromise<int> p([](const QPromiseResolve<int>&) {
|
|
||||||
throw QString("foo");
|
|
||||||
});
|
|
||||||
|
|
||||||
QCOMPARE(p.isRejected(), true);
|
|
||||||
QCOMPARE(waitForValue(p, -1), -1);
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
|
||||||
}
|
|
||||||
{ // resolver(resolve, reject)
|
|
||||||
QPromise<int> p([](const QPromiseResolve<int>&, const QPromiseReject<int>&) {
|
|
||||||
throw QString("foo");
|
|
||||||
});
|
|
||||||
|
|
||||||
QCOMPARE(p.isRejected(), true);
|
|
||||||
QCOMPARE(waitForValue(p, -1), -1);
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::thenReturns()
|
|
||||||
{
|
|
||||||
auto p = QPromise<int>::resolve(42);
|
|
||||||
|
|
||||||
QVariantList values;
|
|
||||||
p.then([&](int res) {
|
|
||||||
values << res;
|
|
||||||
return QString::number(res+1);
|
|
||||||
}).then([&](const QString& res) {
|
|
||||||
values << res;
|
|
||||||
}).then([&]() {
|
|
||||||
values << 44;
|
|
||||||
}).wait();
|
|
||||||
|
|
||||||
QCOMPARE(values, QVariantList({42, QString("43"), 44}));
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::thenThrows()
|
|
||||||
{
|
|
||||||
auto input = QPromise<int>::resolve(42);
|
|
||||||
auto output = input.then([](int res) {
|
|
||||||
throw QString("foo%1").arg(res);
|
|
||||||
return 42;
|
|
||||||
});
|
|
||||||
|
|
||||||
QString error;
|
|
||||||
output.then([&](int res) {
|
|
||||||
error += "bar" + QString::number(res);
|
|
||||||
}).fail([&](const QString& err) {
|
|
||||||
error += err;
|
|
||||||
}).wait();
|
|
||||||
|
|
||||||
QCOMPARE(input.isFulfilled(), true);
|
|
||||||
QCOMPARE(output.isRejected(), true);
|
|
||||||
QCOMPARE(error, QString("foo42"));
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::thenNullPtr()
|
|
||||||
{
|
|
||||||
{ // resolved
|
|
||||||
auto p = QPromise<int>::resolve(42).then(nullptr);
|
|
||||||
|
|
||||||
QCOMPARE(waitForValue(p, -1), 42);
|
|
||||||
QCOMPARE(p.isFulfilled(), true);
|
|
||||||
}
|
|
||||||
{ // rejected
|
|
||||||
auto p = QPromise<int>::reject(QString("foo")).then(nullptr);
|
|
||||||
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
|
||||||
QCOMPARE(p.isRejected(), true);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::thenSkipResult()
|
|
||||||
{
|
|
||||||
auto p = QPromise<int>::resolve(42);
|
|
||||||
|
|
||||||
int value = -1;
|
|
||||||
p.then([&]() {
|
|
||||||
value = 43;
|
|
||||||
}).wait();
|
|
||||||
|
|
||||||
Q_STATIC_ASSERT((std::is_same<decltype(p), QPromise<int> >::value));
|
|
||||||
QCOMPARE(value, 43);
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::thenDelayedResolved()
|
|
||||||
{
|
|
||||||
auto p = QPromise<int>::resolve(42).then([](int res) {
|
|
||||||
return QPromise<QString>([=](const QPromiseResolve<QString>& resolve) {
|
|
||||||
QtPromisePrivate::qtpromise_defer([=]() {
|
|
||||||
resolve(QString("foo%1").arg(res));
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
Q_STATIC_ASSERT((std::is_same<decltype(p), QPromise<QString> >::value));
|
|
||||||
QCOMPARE(waitForValue(p, QString()), QString("foo42"));
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::thenDelayedRejected()
|
|
||||||
{
|
|
||||||
auto p = QPromise<int>::resolve(42).then([](int res) {
|
|
||||||
return QPromise<void>([=](const QPromiseResolve<void>&, const QPromiseReject<void>& reject) {
|
|
||||||
QtPromisePrivate::qtpromise_defer([=]() {
|
|
||||||
reject(QString("foo%1").arg(res));
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
Q_STATIC_ASSERT((std::is_same<decltype(p), QPromise<void> >::value));
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString("foo42"));
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::failSameType()
|
|
||||||
{
|
|
||||||
// http://en.cppreference.com/w/cpp/error/exception
|
|
||||||
auto p = QPromise<int>::reject(std::out_of_range("foo"));
|
|
||||||
|
|
||||||
QString error;
|
|
||||||
p.fail([&](const std::domain_error& e) {
|
|
||||||
error += QString(e.what()) + "0";
|
|
||||||
return -1;
|
|
||||||
}).fail([&](const std::out_of_range& e) {
|
|
||||||
error += QString(e.what()) + "1";
|
|
||||||
return -1;
|
|
||||||
}).fail([&](const std::exception& e) {
|
|
||||||
error += QString(e.what()) + "2";
|
|
||||||
return -1;
|
|
||||||
}).wait();
|
|
||||||
|
|
||||||
QCOMPARE(error, QString("foo1"));
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::failBaseClass()
|
|
||||||
{
|
|
||||||
// http://en.cppreference.com/w/cpp/error/exception
|
|
||||||
auto p = QPromise<int>::reject(std::out_of_range("foo"));
|
|
||||||
|
|
||||||
QString error;
|
|
||||||
p.fail([&](const std::runtime_error& e) {
|
|
||||||
error += QString(e.what()) + "0";
|
|
||||||
return -1;
|
|
||||||
}).fail([&](const std::logic_error& e) {
|
|
||||||
error += QString(e.what()) + "1";
|
|
||||||
return -1;
|
|
||||||
}).fail([&](const std::exception& e) {
|
|
||||||
error += QString(e.what()) + "2";
|
|
||||||
return -1;
|
|
||||||
}).wait();
|
|
||||||
|
|
||||||
QCOMPARE(error, QString("foo1"));
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::failCatchAll()
|
|
||||||
{
|
|
||||||
auto p = QPromise<int>::reject(std::out_of_range("foo"));
|
|
||||||
|
|
||||||
QString error;
|
|
||||||
p.fail([&](const std::runtime_error& e) {
|
|
||||||
error += QString(e.what()) + "0";
|
|
||||||
return -1;
|
|
||||||
}).fail([&]() {
|
|
||||||
error += "bar";
|
|
||||||
return -1;
|
|
||||||
}).fail([&](const std::exception& e) {
|
|
||||||
error += QString(e.what()) + "2";
|
|
||||||
return -1;
|
|
||||||
}).wait();
|
|
||||||
|
|
||||||
QCOMPARE(error, QString("bar"));
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::finallyFulfilled()
|
|
||||||
{
|
|
||||||
int value = -1;
|
|
||||||
auto p = QPromise<int>::resolve(42).finally([&]() {
|
|
||||||
value = 8;
|
|
||||||
return 16; // ignored!
|
|
||||||
});
|
|
||||||
|
|
||||||
Q_STATIC_ASSERT((std::is_same<decltype(p), QPromise<int> >::value));
|
|
||||||
QCOMPARE(waitForValue(p, -1), 42);
|
|
||||||
QCOMPARE(p.isFulfilled(), true);
|
|
||||||
QCOMPARE(value, 8);
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::finallyFulfilled_void()
|
|
||||||
{
|
|
||||||
int value = -1;
|
|
||||||
auto p = QPromise<void>::resolve().finally([&]() {
|
|
||||||
value = 8;
|
|
||||||
return 16; // ignored!
|
|
||||||
});
|
|
||||||
|
|
||||||
Q_STATIC_ASSERT((std::is_same<decltype(p), QPromise<void> >::value));
|
|
||||||
QCOMPARE(waitForValue(p, -1, 42), 42);
|
|
||||||
QCOMPARE(p.isFulfilled(), true);
|
|
||||||
QCOMPARE(value, 8);
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::finallyRejected()
|
|
||||||
{
|
|
||||||
int value = -1;
|
|
||||||
auto p = QPromise<int>::reject(QString("foo")).finally([&]() {
|
|
||||||
value = 8;
|
|
||||||
return 16; // ignored!
|
|
||||||
});
|
|
||||||
|
|
||||||
Q_STATIC_ASSERT((std::is_same<decltype(p), QPromise<int> >::value));
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
|
||||||
QCOMPARE(p.isRejected(), true);
|
|
||||||
QCOMPARE(value, 8);
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::finallyRejected_void()
|
|
||||||
{
|
|
||||||
int value = -1;
|
|
||||||
auto p = QPromise<void>::reject(QString("foo")).finally([&]() {
|
|
||||||
value = 8;
|
|
||||||
return 16; // ignored!
|
|
||||||
});
|
|
||||||
|
|
||||||
Q_STATIC_ASSERT((std::is_same<decltype(p), QPromise<void> >::value));
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
|
||||||
QCOMPARE(p.isRejected(), true);
|
|
||||||
QCOMPARE(value, 8);
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::finallyThrows()
|
|
||||||
{
|
|
||||||
{ // fulfilled
|
|
||||||
auto p = QPromise<int>::resolve(42).finally([&]() {
|
|
||||||
throw QString("bar");
|
|
||||||
});
|
|
||||||
|
|
||||||
Q_STATIC_ASSERT((std::is_same<decltype(p), QPromise<int> >::value));
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString("bar"));
|
|
||||||
QCOMPARE(p.isRejected(), true);
|
|
||||||
}
|
|
||||||
{ // rejected
|
|
||||||
auto p = QPromise<int>::reject(QString("foo")).finally([&]() {
|
|
||||||
throw QString("bar");
|
|
||||||
});
|
|
||||||
|
|
||||||
Q_STATIC_ASSERT((std::is_same<decltype(p), QPromise<int> >::value));
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString("bar"));
|
|
||||||
QCOMPARE(p.isRejected(), true);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::finallyThrows_void()
|
|
||||||
{
|
|
||||||
{ // fulfilled
|
|
||||||
auto p = QPromise<void>::resolve().finally([&]() {
|
|
||||||
throw QString("bar");
|
|
||||||
});
|
|
||||||
|
|
||||||
Q_STATIC_ASSERT((std::is_same<decltype(p), QPromise<void> >::value));
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString("bar"));
|
|
||||||
QCOMPARE(p.isRejected(), true);
|
|
||||||
}
|
|
||||||
{ // rejected
|
|
||||||
auto p = QPromise<void>::reject(QString("foo")).finally([&]() {
|
|
||||||
throw QString("bar");
|
|
||||||
});
|
|
||||||
|
|
||||||
Q_STATIC_ASSERT((std::is_same<decltype(p), QPromise<void> >::value));
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString("bar"));
|
|
||||||
QCOMPARE(p.isRejected(), true);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::finallyDelayedResolved()
|
|
||||||
{
|
|
||||||
{ // fulfilled
|
|
||||||
QVector<int> values;
|
|
||||||
auto p = QPromise<int>::resolve(42).finally([&]() {
|
|
||||||
QPromise<int> p([&](const QPromiseResolve<int>& resolve) {
|
|
||||||
qtpromise_defer([=, &values]() {
|
|
||||||
values << 64;
|
|
||||||
resolve(16); // ignored!
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
values << 8;
|
|
||||||
return p;
|
|
||||||
});
|
|
||||||
|
|
||||||
QCOMPARE(waitForValue(p, -1), 42);
|
|
||||||
QCOMPARE(p.isFulfilled(), true);
|
|
||||||
QCOMPARE(values, QVector<int>({8, 64}));
|
|
||||||
}
|
|
||||||
{ // rejected
|
|
||||||
QVector<int> values;
|
|
||||||
auto p = QPromise<int>::reject(QString("foo")).finally([&]() {
|
|
||||||
QPromise<int> p([&](const QPromiseResolve<int>& resolve) {
|
|
||||||
qtpromise_defer([=, &values]() {
|
|
||||||
values << 64;
|
|
||||||
resolve(16); // ignored!
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
values << 8;
|
|
||||||
return p;
|
|
||||||
});
|
|
||||||
|
|
||||||
p.then([&](int r) {
|
|
||||||
values << r;
|
|
||||||
}).wait();
|
|
||||||
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
|
||||||
QCOMPARE(p.isRejected(), true);
|
|
||||||
QCOMPARE(values, QVector<int>({8, 64}));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::finallyDelayedRejected()
|
|
||||||
{
|
|
||||||
{ // fulfilled
|
|
||||||
auto p = QPromise<int>::resolve(42).finally([]() {
|
|
||||||
return QPromise<int>([](const QPromiseResolve<int>&, const QPromiseReject<int>& reject) {
|
|
||||||
qtpromise_defer([=]() {
|
|
||||||
reject(QString("bar"));
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString("bar"));
|
|
||||||
QCOMPARE(p.isRejected(), true);
|
|
||||||
}
|
|
||||||
{ // rejected
|
|
||||||
auto p = QPromise<int>::reject(QString("foo")).finally([]() {
|
|
||||||
return QPromise<int>([](const QPromiseResolve<int>&, const QPromiseReject<int>& reject) {
|
|
||||||
qtpromise_defer([=]() {
|
|
||||||
reject(QString("bar"));
|
|
||||||
});
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString("bar"));
|
|
||||||
QCOMPARE(p.isRejected(), true);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::tapFulfilled()
|
|
||||||
{
|
|
||||||
int value = -1;
|
|
||||||
auto p = QPromise<int>::resolve(42).tap([&](int res) {
|
|
||||||
value = res + 1;
|
|
||||||
return 8;
|
|
||||||
});
|
|
||||||
|
|
||||||
QCOMPARE(waitForValue(p, 42), 42);
|
|
||||||
QCOMPARE(p.isFulfilled(), true);
|
|
||||||
QCOMPARE(value, 43);
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::tapFulfilled_void()
|
|
||||||
{
|
|
||||||
int value = -1;
|
|
||||||
auto p = QPromise<void>::resolve().tap([&]() {
|
|
||||||
value = 43;
|
|
||||||
return 8;
|
|
||||||
});
|
|
||||||
|
|
||||||
QCOMPARE(waitForValue(p, -1, 42), 42);
|
|
||||||
QCOMPARE(p.isFulfilled(), true);
|
|
||||||
QCOMPARE(value, 43);
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::tapRejected()
|
|
||||||
{
|
|
||||||
int value = -1;
|
|
||||||
auto p = QPromise<int>::reject(QString("foo")).tap([&](int res) {
|
|
||||||
value = res + 1;
|
|
||||||
});
|
|
||||||
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
|
||||||
QCOMPARE(p.isRejected(), true);
|
|
||||||
QCOMPARE(value, -1);
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::tapRejected_void()
|
|
||||||
{
|
|
||||||
int value = -1;
|
|
||||||
auto p = QPromise<void>::reject(QString("foo")).tap([&]() {
|
|
||||||
value = 43;
|
|
||||||
});
|
|
||||||
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
|
||||||
QCOMPARE(p.isRejected(), true);
|
|
||||||
QCOMPARE(value, -1);
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::tapThrows()
|
|
||||||
{
|
|
||||||
auto p = QPromise<int>::resolve(42).tap([&](int) {
|
|
||||||
throw QString("foo");
|
|
||||||
});
|
|
||||||
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
|
||||||
QCOMPARE(p.isRejected(), true);
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::tapThrows_void()
|
|
||||||
{
|
|
||||||
auto p = QPromise<void>::resolve().tap([&]() {
|
|
||||||
throw QString("foo");
|
|
||||||
});
|
|
||||||
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
|
||||||
QCOMPARE(p.isRejected(), true);
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::tapDelayedResolved()
|
|
||||||
{
|
|
||||||
QVector<int> values;
|
|
||||||
auto p = QPromise<int>::resolve(1).tap([&](int) {
|
|
||||||
QPromise<int> p([&](const QPromiseResolve<int>& resolve) {
|
|
||||||
qtpromise_defer([=, &values]() {
|
|
||||||
values << 3;
|
|
||||||
resolve(4); // ignored!
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
values << 2;
|
|
||||||
return p;
|
|
||||||
});
|
|
||||||
|
|
||||||
p.then([&](int r) {
|
|
||||||
values << r;
|
|
||||||
}).wait();
|
|
||||||
|
|
||||||
QCOMPARE(p.isFulfilled(), true);
|
|
||||||
QCOMPARE(values, QVector<int>({2, 3, 1}));
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::tapDelayedRejected()
|
|
||||||
{
|
|
||||||
QVector<int> values;
|
|
||||||
auto p = QPromise<int>::resolve(1).tap([&](int) {
|
|
||||||
QPromise<int> p([&](const QPromiseResolve<int>&, const QPromiseReject<int>& reject) {
|
|
||||||
qtpromise_defer([=, &values]() {
|
|
||||||
values << 3;
|
|
||||||
reject(QString("foo"));
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
values << 2;
|
|
||||||
return p;
|
|
||||||
});
|
|
||||||
|
|
||||||
p.then([&](int r) {
|
|
||||||
values << r;
|
|
||||||
}).wait();
|
|
||||||
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
|
||||||
QCOMPARE(p.isRejected(), true);
|
|
||||||
QCOMPARE(values, QVector<int>({2, 3}));
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::timeoutFulfilled()
|
|
||||||
{
|
|
||||||
QElapsedTimer timer;
|
|
||||||
qint64 elapsed = -1;
|
|
||||||
|
|
||||||
timer.start();
|
|
||||||
|
|
||||||
auto p = QPromise<int>([](const QPromiseResolve<int>& resolve) {
|
|
||||||
QTimer::singleShot(1000, [=]() {
|
|
||||||
resolve(42);
|
|
||||||
});
|
|
||||||
}).timeout(2000).finally([&]() {
|
|
||||||
elapsed = timer.elapsed();
|
|
||||||
});
|
|
||||||
|
|
||||||
QCOMPARE(waitForValue(p, -1), 42);
|
|
||||||
QCOMPARE(p.isFulfilled(), true);
|
|
||||||
QVERIFY(elapsed < 2000);
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::timeoutRejected()
|
|
||||||
{
|
|
||||||
QElapsedTimer timer;
|
|
||||||
qint64 elapsed = -1;
|
|
||||||
|
|
||||||
timer.start();
|
|
||||||
|
|
||||||
auto p = QPromise<int>([](const QPromiseResolve<int>&, const QPromiseReject<int>& reject) {
|
|
||||||
QTimer::singleShot(1000, [=]() {
|
|
||||||
reject(QString("foo"));
|
|
||||||
});
|
|
||||||
}).timeout(2000).finally([&]() {
|
|
||||||
elapsed = timer.elapsed();
|
|
||||||
});
|
|
||||||
|
|
||||||
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
|
||||||
QCOMPARE(p.isRejected(), true);
|
|
||||||
QVERIFY(elapsed < 2000);
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::timeoutReject()
|
|
||||||
{
|
|
||||||
QElapsedTimer timer;
|
|
||||||
qint64 elapsed = -1;
|
|
||||||
bool failed = false;
|
|
||||||
|
|
||||||
timer.start();
|
|
||||||
|
|
||||||
auto p = QPromise<int>([](const QPromiseResolve<int>& resolve) {
|
|
||||||
QTimer::singleShot(4000, [=]() {
|
|
||||||
resolve(42);
|
|
||||||
});
|
|
||||||
}).timeout(2000).finally([&]() {
|
|
||||||
elapsed = timer.elapsed();
|
|
||||||
});
|
|
||||||
|
|
||||||
p.fail([&](const QPromiseTimeoutException&) {
|
|
||||||
failed = true;
|
|
||||||
return -1;
|
|
||||||
}).wait();
|
|
||||||
|
|
||||||
QCOMPARE(waitForValue(p, -1), -1);
|
|
||||||
QCOMPARE(p.isRejected(), true);
|
|
||||||
QCOMPARE(failed, true);
|
|
||||||
QVERIFY(elapsed >= 2000 * 0.95); // Qt::CoarseTimer (default) Coarse timers try to
|
|
||||||
QVERIFY(elapsed <= 2000 * 1.05); // keep accuracy within 5% of the desired interval.
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::delayFulfilled()
|
|
||||||
{
|
|
||||||
QElapsedTimer timer;
|
|
||||||
qint64 elapsed = -1;
|
|
||||||
|
|
||||||
timer.start();
|
|
||||||
|
|
||||||
auto p = QPromise<int>::resolve(42).delay(1000).finally([&]() {
|
|
||||||
elapsed = timer.elapsed();
|
|
||||||
});
|
|
||||||
|
|
||||||
QCOMPARE(waitForValue(p, -1), 42);
|
|
||||||
QCOMPARE(p.isFulfilled(), true);
|
|
||||||
QVERIFY(elapsed >= 1000 * 0.95); // Qt::CoarseTimer (default) Coarse timers try to
|
|
||||||
QVERIFY(elapsed <= 1000 * 1.05); // keep accuracy within 5% of the desired interval.
|
|
||||||
}
|
|
||||||
|
|
||||||
void tst_qpromise::delayRejected()
|
|
||||||
{
|
|
||||||
QElapsedTimer timer;
|
|
||||||
qint64 elapsed = -1;
|
|
||||||
|
|
||||||
timer.start();
|
|
||||||
|
|
||||||
auto p = QPromise<int>::reject(QString("foo")).delay(1000).finally([&]() {
|
|
||||||
elapsed = timer.elapsed();
|
|
||||||
});
|
|
||||||
|
|
||||||
QCOMPARE(waitForError(p, QString()), QString("foo"));
|
|
||||||
QCOMPARE(p.isRejected(), true);
|
|
||||||
QVERIFY(elapsed < 5);
|
|
||||||
}
|
|
@ -15,4 +15,7 @@ coverage {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
HEADERS += \
|
||||||
|
$$PWD/shared/utils.h
|
||||||
|
|
||||||
include(../../../qtpromise.pri)
|
include(../../../qtpromise.pri)
|
||||||
|
@ -5,7 +5,6 @@
|
|||||||
#include <QtTest>
|
#include <QtTest>
|
||||||
|
|
||||||
using namespace QtPromise;
|
using namespace QtPromise;
|
||||||
using namespace QtPromisePrivate;
|
|
||||||
|
|
||||||
// https://promisesaplus.com/#requirements
|
// https://promisesaplus.com/#requirements
|
||||||
class tst_requirements : public QObject
|
class tst_requirements : public QObject
|
||||||
@ -41,7 +40,7 @@ void tst_requirements::statePending()
|
|||||||
// 2.1.1.1. may transition to either the fulfilled state
|
// 2.1.1.1. may transition to either the fulfilled state
|
||||||
{
|
{
|
||||||
QPromise<int> p([&](const QPromiseResolve<int>& resolve) {
|
QPromise<int> p([&](const QPromiseResolve<int>& resolve) {
|
||||||
qtpromise_defer([=]() { resolve(42); });
|
QtPromisePrivate::qtpromise_defer([=]() { resolve(42); });
|
||||||
});
|
});
|
||||||
|
|
||||||
QVERIFY(p.isPending());
|
QVERIFY(p.isPending());
|
||||||
@ -58,7 +57,7 @@ void tst_requirements::statePending()
|
|||||||
// 2.1.1.1. ... or the rejected state
|
// 2.1.1.1. ... or the rejected state
|
||||||
{
|
{
|
||||||
QPromise<int> p([&](const QPromiseResolve<int>&, const QPromiseReject<int>& reject) {
|
QPromise<int> p([&](const QPromiseResolve<int>&, const QPromiseReject<int>& reject) {
|
||||||
qtpromise_defer([=]() { reject(QString("foo")); });
|
QtPromisePrivate::qtpromise_defer([=]() { reject(QString("foo")); });
|
||||||
});
|
});
|
||||||
|
|
||||||
QVERIFY(p.isPending());
|
QVERIFY(p.isPending());
|
||||||
@ -82,7 +81,7 @@ void tst_requirements::stateFulfilled()
|
|||||||
QPromise<int> p([](
|
QPromise<int> p([](
|
||||||
const QPromiseResolve<int>& resolve,
|
const QPromiseResolve<int>& resolve,
|
||||||
const QPromiseReject<int>& reject) {
|
const QPromiseReject<int>& reject) {
|
||||||
qtpromise_defer([=]() {
|
QtPromisePrivate::qtpromise_defer([=]() {
|
||||||
// 2.1.2.2. must have a value, which must not change.
|
// 2.1.2.2. must have a value, which must not change.
|
||||||
resolve(42);
|
resolve(42);
|
||||||
resolve(43);
|
resolve(43);
|
||||||
@ -115,7 +114,7 @@ void tst_requirements::stateRejected()
|
|||||||
QPromise<int> p([](
|
QPromise<int> p([](
|
||||||
const QPromiseResolve<int>& resolve,
|
const QPromiseResolve<int>& resolve,
|
||||||
const QPromiseReject<int>& reject) {
|
const QPromiseReject<int>& reject) {
|
||||||
qtpromise_defer([=]() {
|
QtPromisePrivate::qtpromise_defer([=]() {
|
||||||
// 2.1.3.2. must have a reason, which must not change.
|
// 2.1.3.2. must have a reason, which must not change.
|
||||||
reject(QString("foo"));
|
reject(QString("foo"));
|
||||||
reject(QString("bar"));
|
reject(QString("bar"));
|
||||||
@ -196,7 +195,7 @@ void tst_requirements::thenOnFulfilled()
|
|||||||
// 2.2.2. If onFulfilled is a function:
|
// 2.2.2. If onFulfilled is a function:
|
||||||
QVector<int> values;
|
QVector<int> values;
|
||||||
QPromise<int> p0([](const QPromiseResolve<int>& resolve) {
|
QPromise<int> p0([](const QPromiseResolve<int>& resolve) {
|
||||||
qtpromise_defer([=]() {
|
QtPromisePrivate::qtpromise_defer([=]() {
|
||||||
// 2.2.2.3. it must not be called more than once
|
// 2.2.2.3. it must not be called more than once
|
||||||
resolve(42);
|
resolve(42);
|
||||||
resolve(43);
|
resolve(43);
|
||||||
@ -224,7 +223,7 @@ void tst_requirements::thenOnRejected()
|
|||||||
// 2.2.3. If onRejected is a function:
|
// 2.2.3. If onRejected is a function:
|
||||||
QStringList errors;
|
QStringList errors;
|
||||||
QPromise<void> p0([](const QPromiseResolve<void>&, const QPromiseReject<void>& reject) {
|
QPromise<void> p0([](const QPromiseResolve<void>&, const QPromiseReject<void>& reject) {
|
||||||
qtpromise_defer([=]() {
|
QtPromisePrivate::qtpromise_defer([=]() {
|
||||||
// 2.2.3.3. it must not be called more than once.
|
// 2.2.3.3. it must not be called more than once.
|
||||||
reject(QString("foo"));
|
reject(QString("foo"));
|
||||||
reject(QString("bar"));
|
reject(QString("bar"));
|
||||||
@ -275,7 +274,7 @@ void tst_requirements::thenMultipleCalls()
|
|||||||
{
|
{
|
||||||
QVector<int> values;
|
QVector<int> values;
|
||||||
QPromise<int> p([](const QPromiseResolve<int>& resolve) {
|
QPromise<int> p([](const QPromiseResolve<int>& resolve) {
|
||||||
qtpromise_defer([=]() {
|
QtPromisePrivate::qtpromise_defer([=]() {
|
||||||
resolve(42);
|
resolve(42);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
@ -294,7 +293,7 @@ void tst_requirements::thenMultipleCalls()
|
|||||||
{
|
{
|
||||||
QVector<int> values;
|
QVector<int> values;
|
||||||
QPromise<int> p([](const QPromiseResolve<int>&, const QPromiseReject<int>& reject) {
|
QPromise<int> p([](const QPromiseResolve<int>&, const QPromiseReject<int>& reject) {
|
||||||
qtpromise_defer([=]() {
|
QtPromisePrivate::qtpromise_defer([=]() {
|
||||||
reject(8);
|
reject(8);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
47
tests/auto/qtpromise/shared/utils.h
Normal file
47
tests/auto/qtpromise/shared/utils.h
Normal file
@ -0,0 +1,47 @@
|
|||||||
|
#ifndef QTPROMISE_TESTS_AUTO_SHARED_UTILS_H
|
||||||
|
#define QTPROMISE_TESTS_AUTO_SHARED_UTILS_H
|
||||||
|
|
||||||
|
#include <QtPromise>
|
||||||
|
|
||||||
|
template <typename T>
|
||||||
|
static inline T waitForValue(const QtPromise::QPromise<T>& promise, const T& initial)
|
||||||
|
{
|
||||||
|
T value(initial);
|
||||||
|
promise.then([&](const T& res) {
|
||||||
|
value = res;
|
||||||
|
}).wait();
|
||||||
|
return value;
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename T>
|
||||||
|
static inline T waitForValue(const QtPromise::QPromise<void>& promise, const T& initial, const T& expected)
|
||||||
|
{
|
||||||
|
T value(initial);
|
||||||
|
promise.then([&]() {
|
||||||
|
value = expected;
|
||||||
|
}).wait();
|
||||||
|
return value;
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename T, typename E>
|
||||||
|
static inline E waitForError(const QtPromise::QPromise<T>& promise, const E& initial)
|
||||||
|
{
|
||||||
|
E error(initial);
|
||||||
|
promise.fail([&](const E& err) {
|
||||||
|
error = err;
|
||||||
|
return T();
|
||||||
|
}).wait();
|
||||||
|
return error;
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename E>
|
||||||
|
static inline E waitForError(const QtPromise::QPromise<void>& promise, const E& initial)
|
||||||
|
{
|
||||||
|
E error(initial);
|
||||||
|
promise.fail([&](const E& err) {
|
||||||
|
error = err;
|
||||||
|
}).wait();
|
||||||
|
return error;
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif // QTPROMISE_TESTS_AUTO_SHARED_UTILS_H
|
Loading…
Reference in New Issue
Block a user