diff --git a/src/libs/solutions/tasking/tasktree.cpp b/src/libs/solutions/tasking/tasktree.cpp index 62243f373a1..6f2bb7ad4f5 100644 --- a/src/libs/solutions/tasking/tasktree.cpp +++ b/src/libs/solutions/tasking/tasktree.cpp @@ -404,12 +404,14 @@ TaskItem workflowPolicy(WorkflowPolicy policy) const TaskItem sequential = parallelLimit(1); const TaskItem parallel = parallelLimit(0); + const TaskItem stopOnError = workflowPolicy(WorkflowPolicy::StopOnError); const TaskItem continueOnError = workflowPolicy(WorkflowPolicy::ContinueOnError); const TaskItem stopOnDone = workflowPolicy(WorkflowPolicy::StopOnDone); const TaskItem continueOnDone = workflowPolicy(WorkflowPolicy::ContinueOnDone); const TaskItem stopOnFinished = workflowPolicy(WorkflowPolicy::StopOnFinished); const TaskItem finishAllAndDone = workflowPolicy(WorkflowPolicy::FinishAllAndDone); +const TaskItem finishAllAndError = workflowPolicy(WorkflowPolicy::FinishAllAndError); static TaskAction toTaskAction(bool success) { @@ -859,7 +861,8 @@ TaskContainer::RuntimeData::RuntimeData(const ConstData &constData) , m_storageIdList(createStorages(constData)) { m_successBit = m_constData.m_workflowPolicy != WorkflowPolicy::StopOnDone - && m_constData.m_workflowPolicy != WorkflowPolicy::ContinueOnDone; + && m_constData.m_workflowPolicy != WorkflowPolicy::ContinueOnDone + && m_constData.m_workflowPolicy != WorkflowPolicy::FinishAllAndError; } TaskContainer::RuntimeData::~RuntimeData() @@ -873,7 +876,8 @@ TaskContainer::RuntimeData::~RuntimeData() bool TaskContainer::RuntimeData::updateSuccessBit(bool success) { - if (m_constData.m_workflowPolicy == WorkflowPolicy::FinishAllAndDone) + if (m_constData.m_workflowPolicy == WorkflowPolicy::FinishAllAndDone + || m_constData.m_workflowPolicy == WorkflowPolicy::FinishAllAndError) return m_successBit; if (m_constData.m_workflowPolicy == WorkflowPolicy::StopOnFinished) { m_successBit = success; diff --git a/src/libs/solutions/tasking/tasktree.h b/src/libs/solutions/tasking/tasktree.h index 37403628a5a..c10cf495c31 100644 --- a/src/libs/solutions/tasking/tasktree.h +++ b/src/libs/solutions/tasking/tasktree.h @@ -102,6 +102,7 @@ private: // 3. Stops on first finished child. In sequential mode it will never run other children then the first one. // Useful only in parallel mode. // 4. Always run all children, let them finish, ignore their results and report done afterwards. +// 5. Always run all children, let them finish, ignore their results and report error afterwards. enum class WorkflowPolicy { StopOnError, // 1a - Reports error on first child error, otherwise done (if all children were done). @@ -109,7 +110,8 @@ enum class WorkflowPolicy { StopOnDone, // 2a - Reports done on first child done, otherwise error (if all children were error). ContinueOnDone, // 2b - The same, but children execution continues. Reports error when no children. StopOnFinished, // 3 - Stops on first finished child and report its result. - FinishAllAndDone // 4 - Reports done after all children finished. + FinishAllAndDone, // 4 - Reports done after all children finished. + FinishAllAndError // 5 - Reports error after all children finished. }; Q_ENUM_NS(WorkflowPolicy); @@ -247,12 +249,14 @@ TASKING_EXPORT TaskItem workflowPolicy(WorkflowPolicy policy); TASKING_EXPORT extern const TaskItem sequential; TASKING_EXPORT extern const TaskItem parallel; + TASKING_EXPORT extern const TaskItem stopOnError; TASKING_EXPORT extern const TaskItem continueOnError; TASKING_EXPORT extern const TaskItem stopOnDone; TASKING_EXPORT extern const TaskItem continueOnDone; TASKING_EXPORT extern const TaskItem stopOnFinished; TASKING_EXPORT extern const TaskItem finishAllAndDone; +TASKING_EXPORT extern const TaskItem finishAllAndError; class TASKING_EXPORT Storage : public TaskItem { diff --git a/tests/auto/solutions/tasking/tst_tasking.cpp b/tests/auto/solutions/tasking/tst_tasking.cpp index 051b807842b..ff760169d85 100644 --- a/tests/auto/solutions/tasking/tst_tasking.cpp +++ b/tests/auto/solutions/tasking/tst_tasking.cpp @@ -637,25 +637,36 @@ void tst_Tasking::testTree_data() }; }; - const Log log = {{0, Handler::GroupDone}}; + const Log doneLog = {{0, Handler::GroupDone}}; + const Log errorLog = {{0, Handler::GroupError}}; const Group root1 = createRoot(WorkflowPolicy::StopOnError); - QTest::newRow("EmptyStopOnError") << TestData{storage, root1, log, 0, OnDone::Success}; + QTest::newRow("EmptyStopOnError") << TestData{storage, root1, doneLog, 0, + OnDone::Success}; const Group root2 = createRoot(WorkflowPolicy::ContinueOnError); - QTest::newRow("EmptyContinueOnError") << TestData{storage, root2, log, 0, OnDone::Success}; + QTest::newRow("EmptyContinueOnError") << TestData{storage, root2, doneLog, 0, + OnDone::Success}; const Group root3 = createRoot(WorkflowPolicy::StopOnDone); - QTest::newRow("EmptyStopOnDone") << TestData{storage, root3, log, 0, OnDone::Success}; + QTest::newRow("EmptyStopOnDone") << TestData{storage, root3, doneLog, 0, + OnDone::Success}; const Group root4 = createRoot(WorkflowPolicy::ContinueOnDone); - QTest::newRow("EmptyContinueOnDone") << TestData{storage, root4, log, 0, OnDone::Success}; + QTest::newRow("EmptyContinueOnDone") << TestData{storage, root4, doneLog, 0, + OnDone::Success}; const Group root5 = createRoot(WorkflowPolicy::StopOnFinished); - QTest::newRow("EmptyStopOnFinished") << TestData{storage, root5, log, 0, OnDone::Success}; + QTest::newRow("EmptyStopOnFinished") << TestData{storage, root5, doneLog, 0, + OnDone::Success}; const Group root6 = createRoot(WorkflowPolicy::FinishAllAndDone); - QTest::newRow("EmptyOptional") << TestData{storage, root6, log, 0, OnDone::Success}; + QTest::newRow("EmptyFinishAllAndDone") << TestData{storage, root6, doneLog, 0, + OnDone::Success}; + + const Group root7 = createRoot(WorkflowPolicy::FinishAllAndError); + QTest::newRow("EmptyFinishAllAndError") << TestData{storage, root7, errorLog, 0, + OnDone::Failure}; } { @@ -670,29 +681,45 @@ void tst_Tasking::testTree_data() }; }; - const Log log = { + const Log doneLog = { {1, Handler::Setup}, {1, Handler::Done}, {0, Handler::GroupDone} }; + const Log errorLog = { + {1, Handler::Setup}, + {1, Handler::Done}, + {0, Handler::GroupError} + }; + const Group root1 = createRoot(WorkflowPolicy::StopOnError); - QTest::newRow("DoneStopOnError") << TestData{storage, root1, log, 1, OnDone::Success}; + QTest::newRow("DoneStopOnError") << TestData{storage, root1, doneLog, 1, + OnDone::Success}; const Group root2 = createRoot(WorkflowPolicy::ContinueOnError); - QTest::newRow("DoneContinueOnError") << TestData{storage, root2, log, 1, OnDone::Success}; + QTest::newRow("DoneContinueOnError") << TestData{storage, root2, doneLog, 1, + OnDone::Success}; const Group root3 = createRoot(WorkflowPolicy::StopOnDone); - QTest::newRow("DoneStopOnDone") << TestData{storage, root3, log, 1, OnDone::Success}; + QTest::newRow("DoneStopOnDone") << TestData{storage, root3, doneLog, 1, + OnDone::Success}; const Group root4 = createRoot(WorkflowPolicy::ContinueOnDone); - QTest::newRow("DoneContinueOnDone") << TestData{storage, root4, log, 1, OnDone::Success}; + QTest::newRow("DoneContinueOnDone") << TestData{storage, root4, doneLog, 1, + OnDone::Success}; const Group root5 = createRoot(WorkflowPolicy::StopOnFinished); - QTest::newRow("DoneStopOnFinished") << TestData{storage, root5, log, 1, OnDone::Success}; + QTest::newRow("DoneStopOnFinished") << TestData{storage, root5, doneLog, 1, + OnDone::Success}; const Group root6 = createRoot(WorkflowPolicy::FinishAllAndDone); - QTest::newRow("DoneOptional") << TestData{storage, root6, log, 1, OnDone::Success}; + QTest::newRow("DoneFinishAllAndDone") << TestData{storage, root6, doneLog, 1, + OnDone::Success}; + + const Group root7 = createRoot(WorkflowPolicy::FinishAllAndError); + QTest::newRow("DoneFinishAllAndError") << TestData{storage, root7, errorLog, 1, + OnDone::Failure}; } { @@ -707,35 +734,45 @@ void tst_Tasking::testTree_data() }; }; - const Log log = { - {1, Handler::Setup}, - {1, Handler::Error}, - {0, Handler::GroupError} - }; - - const Log optionalLog = { + const Log doneLog = { {1, Handler::Setup}, {1, Handler::Error}, {0, Handler::GroupDone} }; + const Log errorLog = { + {1, Handler::Setup}, + {1, Handler::Error}, + {0, Handler::GroupError} + }; + const Group root1 = createRoot(WorkflowPolicy::StopOnError); - QTest::newRow("ErrorStopOnError") << TestData{storage, root1, log, 1, OnDone::Failure}; + QTest::newRow("ErrorStopOnError") << TestData{storage, root1, errorLog, 1, + OnDone::Failure}; const Group root2 = createRoot(WorkflowPolicy::ContinueOnError); - QTest::newRow("ErrorContinueOnError") << TestData{storage, root2, log, 1, OnDone::Failure}; + QTest::newRow("ErrorContinueOnError") << TestData{storage, root2, errorLog, 1, + OnDone::Failure}; const Group root3 = createRoot(WorkflowPolicy::StopOnDone); - QTest::newRow("ErrorStopOnDone") << TestData{storage, root3, log, 1, OnDone::Failure}; + QTest::newRow("ErrorStopOnDone") << TestData{storage, root3, errorLog, 1, + OnDone::Failure}; const Group root4 = createRoot(WorkflowPolicy::ContinueOnDone); - QTest::newRow("ErrorContinueOnDone") << TestData{storage, root4, log, 1, OnDone::Failure}; + QTest::newRow("ErrorContinueOnDone") << TestData{storage, root4, errorLog, 1, + OnDone::Failure}; const Group root5 = createRoot(WorkflowPolicy::StopOnFinished); - QTest::newRow("ErrorStopOnFinished") << TestData{storage, root5, log, 1, OnDone::Failure}; + QTest::newRow("ErrorStopOnFinished") << TestData{storage, root5, errorLog, 1, + OnDone::Failure}; const Group root6 = createRoot(WorkflowPolicy::FinishAllAndDone); - QTest::newRow("ErrorOptional") << TestData{storage, root6, optionalLog, 1, OnDone::Success}; + QTest::newRow("ErrorFinishAllAndDone") << TestData{storage, root6, doneLog, 1, + OnDone::Success}; + + const Group root7 = createRoot(WorkflowPolicy::FinishAllAndError); + QTest::newRow("ErrorFinishAllAndError") << TestData{storage, root7, errorLog, 1, + OnDone::Failure}; } { @@ -800,8 +837,12 @@ void tst_Tasking::testTree_data() << TestData{storage, root5, errorErrorLog, 2, OnDone::Failure}; const Group root6 = createRoot(WorkflowPolicy::FinishAllAndDone); - QTest::newRow("StopRootWithOptional") + QTest::newRow("StopRootWithFinishAllAndDone") << TestData{storage, root6, doneLog, 2, OnDone::Success}; + + const Group root7 = createRoot(WorkflowPolicy::FinishAllAndError); + QTest::newRow("StopRootWithFinishAllAndError") + << TestData{storage, root7, errorDoneLog, 2, OnDone::Failure}; } { @@ -884,8 +925,12 @@ void tst_Tasking::testTree_data() << TestData{storage, root5, doneErrorLog, 3, OnDone::Success}; const Group root6 = createRoot(WorkflowPolicy::FinishAllAndDone); - QTest::newRow("StopRootAfterDoneWithOptional") + QTest::newRow("StopRootAfterDoneWithFinishAllAndDone") << TestData{storage, root6, doneDoneLog, 3, OnDone::Success}; + + const Group root7 = createRoot(WorkflowPolicy::FinishAllAndError); + QTest::newRow("StopRootAfterDoneWithFinishAllAndError") + << TestData{storage, root7, errorDoneLog, 3, OnDone::Failure}; } { @@ -948,8 +993,12 @@ void tst_Tasking::testTree_data() << TestData{storage, root5, errorLog, 2, OnDone::Failure}; const Group root6 = createRoot(WorkflowPolicy::FinishAllAndDone); - QTest::newRow("StopGroupWithOptional") + QTest::newRow("StopGroupWithFinishAllAndDone") << TestData{storage, root6, doneLog, 2, OnDone::Failure}; + + const Group root7 = createRoot(WorkflowPolicy::FinishAllAndError); + QTest::newRow("StopGroupWithFinishAllAndError") + << TestData{storage, root7, errorLog, 2, OnDone::Failure}; } { @@ -1026,8 +1075,12 @@ void tst_Tasking::testTree_data() << TestData{storage, root5, shortDoneLog, 3, OnDone::Failure}; const Group root6 = createRoot(WorkflowPolicy::FinishAllAndDone); - QTest::newRow("StopGroupAfterDoneWithOptional") + QTest::newRow("StopGroupAfterDoneWithFinishAllAndDone") << TestData{storage, root6, longDoneLog, 3, OnDone::Failure}; + + const Group root7 = createRoot(WorkflowPolicy::FinishAllAndError); + QTest::newRow("StopGroupAfterDoneWithFinishAllAndError") + << TestData{storage, root7, errorLog, 3, OnDone::Failure}; } { @@ -1104,8 +1157,12 @@ void tst_Tasking::testTree_data() << TestData{storage, root5, shortErrorLog, 3, OnDone::Failure}; const Group root6 = createRoot(WorkflowPolicy::FinishAllAndDone); - QTest::newRow("StopGroupAfterErrorWithOptional") + QTest::newRow("StopGroupAfterErrorWithFinishAllAndDone") << TestData{storage, root6, doneLog, 3, OnDone::Failure}; + + const Group root7 = createRoot(WorkflowPolicy::FinishAllAndError); + QTest::newRow("StopGroupAfterErrorWithFinishAllAndError") + << TestData{storage, root7, longErrorLog, 3, OnDone::Failure}; } { @@ -1133,7 +1190,7 @@ void tst_Tasking::testTree_data() QTest::newRow("StopOnError") << TestData{storage, root1, log1, 3, OnDone::Failure}; const Group root2 = createRoot(WorkflowPolicy::ContinueOnError); - const Log log2 { + const Log errorLog { {1, Handler::Setup}, {1, Handler::Done}, {2, Handler::Setup}, @@ -1142,7 +1199,7 @@ void tst_Tasking::testTree_data() {3, Handler::Done}, {0, Handler::GroupError} }; - QTest::newRow("ContinueOnError") << TestData{storage, root2, log2, 3, OnDone::Failure}; + QTest::newRow("ContinueOnError") << TestData{storage, root2, errorLog, 3, OnDone::Failure}; const Group root3 = createRoot(WorkflowPolicy::StopOnDone); const Log log3 { @@ -1153,7 +1210,7 @@ void tst_Tasking::testTree_data() QTest::newRow("StopOnDone") << TestData{storage, root3, log3, 3, OnDone::Success}; const Group root4 = createRoot(WorkflowPolicy::ContinueOnDone); - const Log log4 { + const Log doneLog { {1, Handler::Setup}, {1, Handler::Done}, {2, Handler::Setup}, @@ -1162,7 +1219,7 @@ void tst_Tasking::testTree_data() {3, Handler::Done}, {0, Handler::GroupDone} }; - QTest::newRow("ContinueOnDone") << TestData{storage, root4, log4, 3, OnDone::Success}; + QTest::newRow("ContinueOnDone") << TestData{storage, root4, doneLog, 3, OnDone::Success}; const Group root5 = createRoot(WorkflowPolicy::StopOnFinished); const Log log5 { @@ -1171,6 +1228,12 @@ void tst_Tasking::testTree_data() {0, Handler::GroupDone} }; QTest::newRow("StopOnFinished") << TestData{storage, root5, log5, 3, OnDone::Success}; + + const Group root6 = createRoot(WorkflowPolicy::FinishAllAndDone); + QTest::newRow("FinishAllAndDone") << TestData{storage, root6, doneLog, 3, OnDone::Success}; + + const Group root7 = createRoot(WorkflowPolicy::FinishAllAndError); + QTest::newRow("FinishAllAndError") << TestData{storage, root7, errorLog, 3, OnDone::Failure}; } { @@ -1213,25 +1276,6 @@ void tst_Tasking::testTree_data() QTest::newRow("StopOnFinished4") << TestData{storage, root4, failure, 2, OnDone::Failure}; } - { - const Group root { - Storage(storage), - finishAllAndDone, - createFailingTask(1), - createFailingTask(2), - groupDone(0), - groupError(0) - }; - const Log log { - {1, Handler::Setup}, - {1, Handler::Error}, - {2, Handler::Setup}, - {2, Handler::Error}, - {0, Handler::GroupDone} - }; - QTest::newRow("Optional") << TestData{storage, root, log, 2, OnDone::Success}; - } - { const auto createRoot = [storage, createSuccessTask, groupDone, groupError]( TaskAction taskAction) {