11#define BOOST_TEST_MODULE testApplicationPVModel
12#include <boost/test/included/unit_test.hpp>
16 using namespace boost::unit_test_framework;
24 const std::unordered_set<std::string>& tags = {})
29 using ctk::ApplicationModule::ApplicationModule;
34 using ctk::VariableGroup::VariableGroup;
44 using ctk::ApplicationModule::ApplicationModule;
49 using ctk::VariableGroup::VariableGroup;
59 using ctk::ModuleGroup::ModuleGroup;
99 "/Deeper/hierarchies/need/tests");
110 BOOST_TEST(invalid.isValid() ==
false);
122 if constexpr(isDirectory(proxy)) {
126 BOOST_FAIL(
"Wrong proxy type found.");
129 BOOST_TEST(found ==
true);
131 BOOST_TEST(dir.
getName() ==
"hierarchies");
134 "/Deeper/hierarchies/notExisting", [&](
auto) { BOOST_FAIL(
"Visitor must not be called."); });
135 BOOST_TEST(found ==
false);
139 if constexpr(isVariable(proxy)) {
143 BOOST_FAIL(
"Wrong proxy type found.");
146 BOOST_TEST(found ==
true);
148 BOOST_TEST(var.
getName() ==
"also");
160 BOOST_CHECK(proxy.
getName() ==
"Deeper/hierarchies");
170 BOOST_CHECK(proxy.
getName() ==
".");
180 BOOST_CHECK(proxy.
getName() ==
"need");
200 BOOST_TEST(pv.
getName() ==
"actuator");
202 BOOST_TEST(nodes.size() == 2);
208 auto checker = [](
auto proxy) {
209 if constexpr(isVariable(proxy)) {
210 BOOST_TEST(proxy.getName() ==
"readBack");
213 BOOST_FAIL(
"Wrong vertex type found");
216 bool found = pv.
visitByPath(
"../readBack", checker);
217 BOOST_TEST(found ==
true);
226 auto dir = app.
myModule.
getModel().
visit(ChimeraTK::Model::returnDirectory, ChimeraTK::Model::getNeighbourDirectory,
228 assert(dir.isValid());
230 BOOST_TEST(dir.getName() ==
"MyModule");
232 auto checker = [](
auto proxy) {
233 if constexpr(isVariable(proxy)) {
234 BOOST_TEST(proxy.getName() ==
"readBack");
237 BOOST_FAIL(
"Wrong vertex type found");
240 bool found = dir.visitByPath(
"./readBack", checker);
241 BOOST_TEST(found ==
true);
250 BOOST_TEST(isRoot(rp) ==
true);
251 BOOST_TEST(isModuleGroup(rp) ==
false);
252 BOOST_TEST(isApplicationModule(rp) ==
false);
253 BOOST_TEST(isVariableGroup(rp) ==
false);
254 BOOST_TEST(isDeviceModule(rp) ==
false);
255 BOOST_TEST(isVariable(rp) ==
false);
256 BOOST_TEST(isDirectory(rp) ==
false);
257 BOOST_TEST(hasName(rp) ==
false);
260 BOOST_TEST(isRoot(mgp) ==
false);
261 BOOST_TEST(isModuleGroup(mgp) ==
true);
262 BOOST_TEST(isApplicationModule(mgp) ==
false);
263 BOOST_TEST(isVariableGroup(mgp) ==
false);
264 BOOST_TEST(isDeviceModule(mgp) ==
false);
265 BOOST_TEST(isVariable(mgp) ==
false);
266 BOOST_TEST(isDirectory(mgp) ==
false);
267 BOOST_TEST(hasName(mgp) ==
true);
270 BOOST_TEST(isRoot(amp) ==
false);
271 BOOST_TEST(isModuleGroup(amp) ==
false);
272 BOOST_TEST(isApplicationModule(amp) ==
true);
273 BOOST_TEST(isVariableGroup(amp) ==
false);
274 BOOST_TEST(isDeviceModule(amp) ==
false);
275 BOOST_TEST(isVariable(amp) ==
false);
276 BOOST_TEST(isDirectory(amp) ==
false);
277 BOOST_TEST(hasName(amp) ==
true);
280 BOOST_TEST(isRoot(vgp) ==
false);
281 BOOST_TEST(isModuleGroup(vgp) ==
false);
282 BOOST_TEST(isApplicationModule(vgp) ==
false);
283 BOOST_TEST(isVariableGroup(vgp) ==
true);
284 BOOST_TEST(isDeviceModule(vgp) ==
false);
285 BOOST_TEST(isVariable(vgp) ==
false);
286 BOOST_TEST(isDirectory(vgp) ==
false);
287 BOOST_TEST(hasName(vgp) ==
true);
290 BOOST_TEST(isRoot(dmp) ==
false);
291 BOOST_TEST(isModuleGroup(dmp) ==
false);
292 BOOST_TEST(isApplicationModule(dmp) ==
false);
293 BOOST_TEST(isVariableGroup(dmp) ==
false);
294 BOOST_TEST(isDeviceModule(dmp) ==
true);
295 BOOST_TEST(isVariable(dmp) ==
false);
296 BOOST_TEST(isDirectory(dmp) ==
false);
297 BOOST_TEST(hasName(dmp) ==
false);
300 BOOST_TEST(isRoot(pvp) ==
false);
301 BOOST_TEST(isModuleGroup(pvp) ==
false);
302 BOOST_TEST(isApplicationModule(pvp) ==
false);
303 BOOST_TEST(isVariableGroup(pvp) ==
false);
304 BOOST_TEST(isDeviceModule(pvp) ==
false);
305 BOOST_TEST(isVariable(pvp) ==
true);
306 BOOST_TEST(isDirectory(pvp) ==
false);
307 BOOST_TEST(hasName(pvp) ==
true);
310 BOOST_TEST(isRoot(dp) ==
false);
311 BOOST_TEST(isModuleGroup(dp) ==
false);
312 BOOST_TEST(isApplicationModule(dp) ==
false);
313 BOOST_TEST(isVariableGroup(dp) ==
false);
314 BOOST_TEST(isDeviceModule(dp) ==
false);
315 BOOST_TEST(isVariable(dp) ==
false);
316 BOOST_TEST(isDirectory(dp) ==
true);
317 BOOST_TEST(hasName(dp) ==
true);
326 BOOST_TEST(isRoot(rp) ==
true);
327 BOOST_TEST(isModuleGroup(rp) ==
false);
328 BOOST_TEST(isApplicationModule(rp) ==
false);
329 BOOST_TEST(isVariableGroup(rp) ==
false);
330 BOOST_TEST(isDeviceModule(rp) ==
false);
331 BOOST_TEST(isVariable(rp) ==
false);
332 BOOST_TEST(isDirectory(rp) ==
false);
333 BOOST_TEST(hasName(rp) ==
false);
336 BOOST_TEST(isRoot(mgp) ==
false);
337 BOOST_TEST(isModuleGroup(mgp) ==
true);
338 BOOST_TEST(isApplicationModule(mgp) ==
false);
339 BOOST_TEST(isVariableGroup(mgp) ==
false);
340 BOOST_TEST(isDeviceModule(mgp) ==
false);
341 BOOST_TEST(isVariable(mgp) ==
false);
342 BOOST_TEST(isDirectory(mgp) ==
false);
343 BOOST_TEST(hasName(mgp) ==
true);
346 BOOST_TEST(isRoot(amp) ==
false);
347 BOOST_TEST(isModuleGroup(amp) ==
false);
348 BOOST_TEST(isApplicationModule(amp) ==
true);
349 BOOST_TEST(isVariableGroup(amp) ==
false);
350 BOOST_TEST(isDeviceModule(amp) ==
false);
351 BOOST_TEST(isVariable(amp) ==
false);
352 BOOST_TEST(isDirectory(amp) ==
false);
353 BOOST_TEST(hasName(amp) ==
true);
356 BOOST_TEST(isRoot(vgp) ==
false);
357 BOOST_TEST(isModuleGroup(vgp) ==
false);
358 BOOST_TEST(isApplicationModule(vgp) ==
false);
359 BOOST_TEST(isVariableGroup(vgp) ==
true);
360 BOOST_TEST(isDeviceModule(vgp) ==
false);
361 BOOST_TEST(isVariable(vgp) ==
false);
362 BOOST_TEST(isDirectory(vgp) ==
false);
363 BOOST_TEST(hasName(vgp) ==
true);
366 BOOST_TEST(isRoot(dmp) ==
false);
367 BOOST_TEST(isModuleGroup(dmp) ==
false);
368 BOOST_TEST(isApplicationModule(dmp) ==
false);
369 BOOST_TEST(isVariableGroup(dmp) ==
false);
370 BOOST_TEST(isDeviceModule(dmp) ==
true);
371 BOOST_TEST(isVariable(dmp) ==
false);
372 BOOST_TEST(isDirectory(dmp) ==
false);
373 BOOST_TEST(hasName(dmp) ==
false);
376 BOOST_TEST(isRoot(pvp) ==
false);
377 BOOST_TEST(isModuleGroup(pvp) ==
false);
378 BOOST_TEST(isApplicationModule(pvp) ==
false);
379 BOOST_TEST(isVariableGroup(pvp) ==
false);
380 BOOST_TEST(isDeviceModule(pvp) ==
false);
381 BOOST_TEST(isVariable(pvp) ==
true);
382 BOOST_TEST(isDirectory(pvp) ==
false);
383 BOOST_TEST(hasName(pvp) ==
true);
386 BOOST_TEST(isRoot(dp) ==
false);
387 BOOST_TEST(isModuleGroup(dp) ==
false);
388 BOOST_TEST(isApplicationModule(dp) ==
false);
389 BOOST_TEST(isVariableGroup(dp) ==
false);
390 BOOST_TEST(isDeviceModule(dp) ==
false);
391 BOOST_TEST(isVariable(dp) ==
false);
392 BOOST_TEST(isDirectory(dp) ==
true);
393 BOOST_TEST(hasName(dp) ==
true);
405 size_t foundElements = 0;
407 auto checker = [&](
auto proxy) {
411 BOOST_TEST(proxy.getAliasOrCdd() ==
"Dummy0");
417 BOOST_FAIL(
"Wrong vertex type found");
421 app.
getModel().
visit(checker, ChimeraTK::Model::adjacentInSearch);
423 BOOST_TEST(foundElements == 2);
428 size_t foundElements = 0;
430 auto checker = [&](
auto proxy) {
434 BOOST_TEST(proxy.getName() ==
"readBack");
440 BOOST_FAIL(
"Wrong vertex type found");
446 BOOST_TEST(foundElements == 2);
457 size_t foundElements = 0;
459 auto checker = [&](
auto proxy) {
463 BOOST_TEST(proxy.getAliasOrCdd() ==
"Dummy0");
467 const auto& name = proxy.getName();
468 BOOST_CHECK(name ==
"Deeper" || name ==
"MyModule" || name ==
"somepath" || name ==
"Devices");
472 const auto& name = proxy.getName();
473 BOOST_CHECK(name ==
"Deeper/hierarchies");
476 const auto& name = proxy.getName();
477 BOOST_CHECK(name ==
"MyModule" || name ==
"Deeper/MyModule" || name ==
"/Devices/Dummy0");
483 BOOST_FAIL(
"Wrong vertex type found");
487 app.
getModel().
visit(checker, ChimeraTK::Model::adjacentOutSearch);
489 BOOST_TEST(foundElements == 10);
494 size_t foundElements = 0;
496 auto checker = [&](
auto proxy) {
500 BOOST_CHECK(proxy.getName() ==
"actuator");
504 BOOST_CHECK(proxy.getName() ==
"MyModule");
508 BOOST_CHECK(proxy.getName() ==
"pointlessVariableGroup");
511 BOOST_FAIL(
"Wrong vertex type found");
517 BOOST_TEST(foundElements == 4);
525 template<
typename PROXY>
552 std::set<Item> items;
553 size_t itemsToFind = 0;
554 auto collector = [&](
auto proxy) {
555 Item itemToInsert(proxy);
556 items.insert(itemToInsert);
560 app.
getModel().
visit(collector, ChimeraTK::Model::adjacentOutSearch);
561 app.
getModel().
visit(collector, ChimeraTK::Model::adjacentInSearch);
564 size_t itemsFound = 0;
565 auto finder = [&](
auto proxy) {
566 Item itemToFind(proxy);
568 BOOST_CHECK(items.find(itemToFind) != items.end());
571 app.
getModel().
visit(finder, ChimeraTK::Model::adjacentSearch);
573 BOOST_TEST(itemsFound == itemsToFind);
581 std::vector<std::string> pvNames;
583 auto pvNamesFiller = [&](
auto proxy) { pvNames.push_back(proxy.getFullyQualifiedPath()); };
585 app.
getModel().
visit(pvNamesFiller, ChimeraTK::Model::depthFirstSearch, ChimeraTK::Model::keepDirectories,
586 ChimeraTK::Model::keepParenthood);
588 BOOST_TEST(pvNames.size() == 10);
591 BOOST_CHECK(std::find(pvNames.begin(), pvNames.end(),
"/Deeper") != pvNames.end());
592 BOOST_CHECK(std::find(pvNames.begin(), pvNames.end(),
"/Deeper/hierarchies") != pvNames.end());
593 BOOST_CHECK(std::find(pvNames.begin(), pvNames.end(),
"/Deeper/hierarchies/need") != pvNames.end());
594 BOOST_CHECK(std::find(pvNames.begin(), pvNames.end(),
"/Deeper/MyModule") != pvNames.end());
595 BOOST_CHECK(std::find(pvNames.begin(), pvNames.end(),
"/Deeper/MyModule/pointlessVariableGroup") != pvNames.end());
596 BOOST_CHECK(std::find(pvNames.begin(), pvNames.end(),
"/somepath") != pvNames.end());
597 BOOST_CHECK(std::find(pvNames.begin(), pvNames.end(),
"/MyModule") != pvNames.end());
598 BOOST_CHECK(std::find(pvNames.begin(), pvNames.end(),
"/MyModule/pointlessVariableGroup") != pvNames.end());
599 BOOST_CHECK(std::find(pvNames.begin(), pvNames.end(),
"/Devices") != pvNames.end());
600 BOOST_CHECK(std::find(pvNames.begin(), pvNames.end(),
"/Devices/Dummy0") != pvNames.end());
609 auto deeperHierarchies = std::find(pvNames.begin(), pvNames.end(),
"/Deeper/hierarchies");
610 auto deeperHierarchiesNeed = std::find(pvNames.begin(), pvNames.end(),
"/Deeper/hierarchies/need");
611 auto deeperMyModule = std::find(pvNames.begin(), pvNames.end(),
"/Deeper/MyModule");
612 auto deeperMyModulePVG = std::find(pvNames.begin(), pvNames.end(),
"/Deeper/MyModule/pointlessVariableGroup");
614 BOOST_CHECK((deeperHierarchies < deeperMyModule && deeperHierarchiesNeed < deeperMyModule) ||
615 (deeperMyModule < deeperHierarchies && deeperMyModulePVG < deeperHierarchies));
623 std::vector<std::string> pvNames;
625 auto pvNamesFiller = [&](
auto proxy) { pvNames.push_back(proxy.getFullyQualifiedPath()); };
627 app.
getModel().
visit(pvNamesFiller, ChimeraTK::Model::breadthFirstSearch, ChimeraTK::Model::keepDirectories,
628 ChimeraTK::Model::keepParenthood);
630 BOOST_TEST(pvNames.size() == 10);
633 BOOST_CHECK(std::find(pvNames.begin(), pvNames.end(),
"/Deeper") != pvNames.end());
634 BOOST_CHECK(std::find(pvNames.begin(), pvNames.end(),
"/Deeper/hierarchies") != pvNames.end());
635 BOOST_CHECK(std::find(pvNames.begin(), pvNames.end(),
"/Deeper/hierarchies/need") != pvNames.end());
636 BOOST_CHECK(std::find(pvNames.begin(), pvNames.end(),
"/Deeper/MyModule") != pvNames.end());
637 BOOST_CHECK(std::find(pvNames.begin(), pvNames.end(),
"/Deeper/MyModule/pointlessVariableGroup") != pvNames.end());
638 BOOST_CHECK(std::find(pvNames.begin(), pvNames.end(),
"/somepath") != pvNames.end());
639 BOOST_CHECK(std::find(pvNames.begin(), pvNames.end(),
"/MyModule") != pvNames.end());
640 BOOST_CHECK(std::find(pvNames.begin(), pvNames.end(),
"/MyModule/pointlessVariableGroup") != pvNames.end());
641 BOOST_CHECK(std::find(pvNames.begin(), pvNames.end(),
"/Devices") != pvNames.end());
642 BOOST_CHECK(std::find(pvNames.begin(), pvNames.end(),
"/Devices/Dummy0") != pvNames.end());
645 auto deeperHierarchies = std::find(pvNames.begin(), pvNames.end(),
"/Deeper/hierarchies");
646 auto deeperHierarchiesNeed = std::find(pvNames.begin(), pvNames.end(),
"/Deeper/hierarchies/need");
647 auto deeperMyModule = std::find(pvNames.begin(), pvNames.end(),
"/Deeper/MyModule");
648 auto deeperMyModulePVG = std::find(pvNames.begin(), pvNames.end(),
"/Deeper/MyModule/pointlessVariableGroup");
650 BOOST_CHECK(deeperHierarchies < deeperHierarchiesNeed);
651 BOOST_CHECK(deeperMyModule < deeperHierarchiesNeed);
652 BOOST_CHECK(deeperHierarchies < deeperMyModulePVG);
653 BOOST_CHECK(deeperMyModule < deeperMyModulePVG);
665 size_t foundElements = 0;
667 auto checker = [&](
auto proxy) {
670 BOOST_CHECK(proxy.getName() ==
"readBack" || proxy.getName() ==
"actuator");
673 BOOST_FAIL(
"Wrong vertex type found");
677 app.
myModule.
getModel().
visit(checker, ChimeraTK::Model::keepPvAccess, ChimeraTK::Model::adjacentSearch);
679 BOOST_TEST(foundElements == 2);
684 size_t foundElements = 0;
686 auto checker = [&](
auto proxy) {
689 BOOST_CHECK(proxy.getAliasOrCdd() ==
"Dummy0");
692 BOOST_CHECK(proxy.getName() ==
"MyModule");
695 BOOST_FAIL(
"Wrong vertex type found");
700 checker, ChimeraTK::Model::keepPvAccess, ChimeraTK::Model::adjacentSearch);
702 BOOST_TEST(foundElements == 2);
713 size_t foundElements = 0;
715 auto checker = [&](
auto proxy) {
718 BOOST_CHECK(proxy.getName() ==
"actuator");
721 BOOST_CHECK(proxy.getName() ==
"pointlessVariableGroup");
726 BOOST_FAIL(
"Wrong vertex type found");
730 app.
myModule.
getModel().
visit(checker, ChimeraTK::Model::keepOwnership, ChimeraTK::Model::adjacentSearch);
732 BOOST_TEST(foundElements == 3);
737 size_t foundElements = 0;
739 auto checker = [&](
auto proxy) {
742 BOOST_CHECK(proxy.getName() ==
"pointlessVariableGroup");
745 BOOST_CHECK(proxy.getAliasOrCdd() ==
"Dummy0");
748 BOOST_FAIL(
"Wrong vertex type found");
753 checker, ChimeraTK::Model::keepOwnership, ChimeraTK::Model::adjacentSearch);
755 BOOST_TEST(foundElements == 2);
768 app.
myModule.
getModel().
visit(ChimeraTK::Model::returnDirectory, ChimeraTK::Model::getNeighbourDirectory,
770 assert(dir.isValid());
772 size_t foundElements = 0;
774 auto checker = [&](
auto proxy) {
777 BOOST_CHECK(proxy.getName() ==
"actuator" || proxy.getName() ==
"readBack");
780 BOOST_CHECK(proxy.getName() ==
"pointlessVariableGroup");
785 BOOST_FAIL(
"Wrong vertex type found");
789 dir.visit(checker, ChimeraTK::Model::keepParenthood, ChimeraTK::Model::adjacentSearch);
791 BOOST_TEST(foundElements == 4);
796 size_t foundElements = 0;
798 auto checker = [&](
auto proxy) {
801 BOOST_CHECK(proxy.getName() ==
"MyModule");
804 BOOST_FAIL(
"Wrong vertex type found");
809 checker, ChimeraTK::Model::keepParenthood, ChimeraTK::Model::adjacentSearch);
811 BOOST_TEST(foundElements == 1);
822 size_t foundElements = 0;
824 auto checker = [&](
auto proxy) {
827 BOOST_CHECK(proxy.getName() ==
"MyModule");
830 BOOST_FAIL(
"Wrong vertex type found");
834 app.
myModule.
getModel().
visit(checker, ChimeraTK::Model::keepNeighbourhood, ChimeraTK::Model::adjacentOutSearch);
836 BOOST_TEST(foundElements == 1);
843 [[maybe_unused]]
auto found = app.
getModel().
visitByPath(
"/Deeper/hierarchies", [&](
auto proxy) {
850 size_t foundElements = 0;
852 auto checker = [&](
auto proxy) {
855 BOOST_CHECK(proxy.getName() ==
"Deeper/hierarchies");
858 BOOST_CHECK(proxy.getName() ==
".");
861 BOOST_FAIL(
"Wrong vertex type found");
865 dir.
visit(checker, ChimeraTK::Model::keepNeighbourhood, ChimeraTK::Model::adjacentInSearch);
867 BOOST_TEST(foundElements == 2);
880 size_t foundElements = 0;
882 auto checker = [&](
auto proxy) {
885 BOOST_CHECK(proxy.getName() ==
"Deeper/hierarchies");
888 BOOST_FAIL(
"Wrong vertex type found");
892 app.
getModel().
visit(checker, ChimeraTK::Model::keepModuleGroups, ChimeraTK::Model::adjacentSearch);
894 BOOST_TEST(foundElements == 1);
899 size_t foundElements = 0;
901 auto checker = [&](
auto proxy) {
904 BOOST_CHECK(proxy.getName() ==
"Deeper/hierarchies");
907 BOOST_FAIL(
"Wrong vertex type found");
912 checker, ChimeraTK::Model::keepModuleGroups, ChimeraTK::Model::adjacentSearch);
914 BOOST_TEST(foundElements == 1);
925 size_t foundElements = 0;
927 auto checker = [&](
auto proxy) {
930 BOOST_CHECK(proxy.getName() ==
".");
933 BOOST_FAIL(
"Wrong vertex type found");
938 checker, ChimeraTK::Model::keepApplicationModules, ChimeraTK::Model::adjacentSearch);
940 BOOST_TEST(foundElements == 1);
945 size_t foundElements = 0;
947 auto checker = [&](
auto proxy) {
950 BOOST_CHECK(proxy.getName() ==
".");
953 BOOST_FAIL(
"Wrong vertex type found");
958 checker, ChimeraTK::Model::keepApplicationModules, ChimeraTK::Model::adjacentSearch);
960 BOOST_TEST(foundElements ==
972 size_t foundElements = 0;
974 auto checker = [&](
auto proxy) {
977 BOOST_CHECK(proxy.getName() ==
"pointlessVariableGroup");
980 BOOST_FAIL(
"Wrong vertex type found");
984 app.
myModule.
getModel().
visit(checker, ChimeraTK::Model::keepVariableGroups, ChimeraTK::Model::adjacentSearch);
986 BOOST_TEST(foundElements == 1);
991 size_t foundElements = 0;
993 auto checker = [&](
auto proxy) {
996 BOOST_CHECK(proxy.getName() ==
"need");
999 BOOST_FAIL(
"Wrong vertex type found");
1004 checker, ChimeraTK::Model::keepVariableGroups, ChimeraTK::Model::adjacentSearch);
1006 BOOST_TEST(foundElements == 1);
1017 size_t foundElements = 0;
1019 auto checker = [&](
auto proxy) {
1022 BOOST_CHECK(proxy.getAliasOrCdd() ==
"Dummy0");
1025 BOOST_FAIL(
"Wrong vertex type found");
1029 app.
getModel().
visit(checker, ChimeraTK::Model::keepDeviceModules, ChimeraTK::Model::adjacentSearch);
1031 BOOST_TEST(foundElements == 2);
1036 size_t foundElements = 0;
1038 auto checker = [&](
auto proxy) {
1041 BOOST_CHECK(proxy.getAliasOrCdd() ==
"Dummy0");
1044 BOOST_FAIL(
"Wrong vertex type found");
1049 checker, ChimeraTK::Model::keepDeviceModules, ChimeraTK::Model::adjacentSearch);
1051 BOOST_TEST(foundElements == 2);
1062 size_t foundElements = 0;
1064 auto checker = [&](
auto proxy) {
1067 BOOST_CHECK(proxy.getName() ==
"readBack" || proxy.getName() ==
"actuator");
1070 BOOST_FAIL(
"Wrong vertex type found");
1074 app.
myModule.
getModel().
visit(checker, ChimeraTK::Model::keepProcessVariables, ChimeraTK::Model::adjacentSearch);
1076 BOOST_TEST(foundElements == 3);
1083 [[maybe_unused]]
auto found = app.
getModel().
visitByPath(
"/Deeper/hierarchies", [&](
auto proxy) {
1090 size_t foundElements = 0;
1092 auto checker = [&](
auto proxy) {
1095 BOOST_CHECK(proxy.getName() ==
"also");
1098 BOOST_FAIL(
"Wrong vertex type found");
1102 dir.
visit(checker, ChimeraTK::Model::keepProcessVariables, ChimeraTK::Model::adjacentSearch);
1104 BOOST_TEST(foundElements == 1);
1115 size_t foundElements = 0;
1117 auto checker = [&](
auto proxy) {
1120 BOOST_CHECK(proxy.getName() ==
"MyModule");
1123 BOOST_FAIL(
"Wrong vertex type found");
1127 app.
myModule.
getModel().
visit(checker, ChimeraTK::Model::keepDirectories, ChimeraTK::Model::adjacentSearch);
1129 BOOST_TEST(foundElements == 1);
1136 [[maybe_unused]]
auto found = app.
getModel().
visitByPath(
"/Deeper/hierarchies", [&](
auto proxy) {
1143 size_t foundElements = 0;
1145 auto checker = [&](
auto proxy) {
1148 BOOST_CHECK(proxy.getName() ==
"Deeper" || proxy.getName() ==
"need");
1151 BOOST_FAIL(
"Wrong vertex type found");
1155 dir.
visit(checker, ChimeraTK::Model::keepDirectories, ChimeraTK::Model::adjacentSearch);
1157 BOOST_TEST(foundElements == 2);
1168 size_t foundElements = 0;
1170 auto checker = [&](
auto proxy) {
1173 BOOST_CHECK(proxy.getName() ==
"MyModule");
1176 BOOST_CHECK(proxy.getName() ==
"MyModule");
1179 BOOST_FAIL(
"Wrong vertex type found");
1183 app.
getModel().
visit(checker, ChimeraTK::Model::keepName(
"MyModule"), ChimeraTK::Model::adjacentSearch);
1185 BOOST_TEST(foundElements == 2);
1196 size_t foundElements = 0;
1198 auto checker = [&](
auto proxy) {
1200 BOOST_CHECK(proxy.getFullyQualifiedPath() ==
"/Deeper/hierarchies/also" ||
1201 proxy.getFullyQualifiedPath() ==
"/Deeper/hierarchies/need/tests");
1204 app.
getModel().
visit(checker, ChimeraTK::Model::keepTag(
"A"), ChimeraTK::Model::depthFirstSearch,
1205 ChimeraTK::Model::keepProcessVariables);
1207 BOOST_TEST(foundElements == 2);
1212 size_t foundElements = 0;
1214 auto checker = [&](
auto proxy) {
1216 BOOST_CHECK(proxy.getFullyQualifiedPath() ==
"/MyModule/actuator" ||
1217 proxy.getFullyQualifiedPath() ==
"/Deeper/MyModule/actuator" ||
1218 proxy.getFullyQualifiedPath() ==
"/Deeper/hierarchies/need/tests");
1221 app.
getModel().
visit(checker, ChimeraTK::Model::keepTag(
"B"), ChimeraTK::Model::depthFirstSearch,
1222 ChimeraTK::Model::keepProcessVariables);
1224 BOOST_TEST(foundElements == 3);
1237 auto returnAlias = [&](
auto proxy) -> std::string {
return proxy.getAliasOrCdd(); };
1238 alias = app.
getModel().
visit(returnAlias, ChimeraTK::Model::depthFirstSearch, ChimeraTK::Model::keepDeviceModules,
1240 BOOST_TEST(alias ==
"Dummy0");
1244 auto setAlias = [&](
auto proxy) ->
void { alias = proxy.getAliasOrCdd(); };
1245 app.
getModel().
visit(setAlias, ChimeraTK::Model::depthFirstSearch, ChimeraTK::Model::keepDeviceModules,
1247 BOOST_TEST(alias ==
"Dummy0");
1256 auto countHits = [&](
auto) { ++hits; };
1257 app.
getModel().
visit(countHits, ChimeraTK::Model::depthFirstSearch, ChimeraTK::Model::keepPvAccess,
1258 ChimeraTK::Model::keepProcessVariables);
1262 BOOST_TEST(hits == 0);
1266 app.
getModel().
visit(countHits, ChimeraTK::Model::depthFirstSearch, ChimeraTK::Model::keepPvAccess,
1267 ChimeraTK::Model::keepProcessVariables, ChimeraTK::Model::continueSearchDisjunctTrees);
1268 BOOST_TEST(hits == 10);
1278 size_t foundElements = 0;
1280 auto checker = [&](
auto proxy) {
1283 BOOST_CHECK(proxy.getName() ==
"Deeper/hierarchies");
1286 BOOST_CHECK(proxy.getAliasOrCdd() ==
"Dummy0");
1289 BOOST_FAIL(
"Wrong vertex type found");
1293 app.
getModel().
visit(checker, ChimeraTK::Model::keepModuleGroups || ChimeraTK::Model::keepDeviceModules,
1294 ChimeraTK::Model::adjacentSearch);
1296 BOOST_TEST(foundElements == 3);
1304 size_t foundElements = 0;
1306 auto checker = [&](
auto proxy) {
1309 BOOST_CHECK(proxy.getName() ==
"Deeper/hierarchies");
1312 BOOST_FAIL(
"Wrong vertex type found");
1317 ChimeraTK::Model::keepModuleGroups && ChimeraTK::Model::keepName(
"Deeper/hierarchies"),
1318 ChimeraTK::Model::adjacentSearch);
1320 BOOST_TEST(foundElements == 1);
1328 size_t foundElements = 0;
1330 auto checker = [&](
auto proxy) {
1333 BOOST_CHECK(proxy.getName() ==
"Deeper/hierarchies");
1336 BOOST_CHECK(proxy.getAliasOrCdd() ==
"Dummy0");
1339 BOOST_FAIL(
"Wrong vertex type found");
1344 (ChimeraTK::Model::keepModuleGroups && ChimeraTK::Model::keepName(
"Deeper/hierarchies")) ||
1345 ChimeraTK::Model::keepDeviceModules,
1346 ChimeraTK::Model::adjacentOutSearch);
1348 BOOST_TEST(foundElements == 2);
1353 ChimeraTK::Model::keepDeviceModules ||
1354 (ChimeraTK::Model::keepModuleGroups && ChimeraTK::Model::keepName(
"Deeper/hierarchies")),
1355 ChimeraTK::Model::adjacentOutSearch);
1357 BOOST_TEST(foundElements == 2);
1365 size_t foundElements = 0;
1367 auto checker = [&](
auto proxy) {
1370 BOOST_CHECK(proxy.getName() ==
"MyModule");
1373 BOOST_CHECK(proxy.getName() ==
"MyModule");
1376 BOOST_FAIL(
"Wrong vertex type found");
1381 (ChimeraTK::Model::keepApplicationModules || ChimeraTK::Model::keepDirectories) &&
1382 ChimeraTK::Model::keepName(
"MyModule"),
1383 ChimeraTK::Model::adjacentOutSearch);
1385 BOOST_TEST(foundElements == 2);
1390 ChimeraTK::Model::keepName(
"MyModule") &&
1391 (ChimeraTK::Model::keepApplicationModules || ChimeraTK::Model::keepDirectories),
1392 ChimeraTK::Model::adjacentOutSearch);
1394 BOOST_TEST(foundElements == 2);
1402 size_t foundElements = 0;
1404 auto checker = [&](
auto proxy) {
1407 BOOST_CHECK(proxy.getAliasOrCdd() ==
"Dummy0");
1410 BOOST_CHECK(proxy.getName() ==
"Deeper" || proxy.getName() ==
"MyModule" || proxy.getName() ==
"somepath" ||
1411 proxy.getName() ==
"Devices");
1416 BOOST_FAIL(
"Wrong vertex type found");
1420 app.
getModel().
visit(checker, ChimeraTK::Model::keepNeighbourhood || ChimeraTK::Model::keepParenthood,
1421 ChimeraTK::Model::adjacentSearch);
1423 BOOST_TEST(foundElements == 7);
1436 size_t foundElements = 0;
1438 auto checker = [&](
auto proxy) {
1441 BOOST_CHECK(proxy.getName() ==
"Deeper/hierarchies");
1444 BOOST_FAIL(
"Wrong vertex type found");
1448 app.
getModel().
visit(checker, ChimeraTK::Model::ownedModuleGroups);
1450 BOOST_TEST(foundElements == 1);
1460 size_t foundElements = 0;
1462 auto checker = [&](
auto proxy) {
1465 BOOST_CHECK(proxy.getName() ==
".");
1468 BOOST_FAIL(
"Wrong vertex type found");
1474 BOOST_TEST(foundElements == 1);
1484 size_t foundElements = 0;
1486 auto checker = [&](
auto proxy) {
1489 BOOST_CHECK(proxy.getName() ==
"need");
1492 BOOST_FAIL(
"Wrong vertex type found");
1498 BOOST_TEST(foundElements == 1);
1508 size_t foundElements = 0;
1510 auto checker = [&](
auto proxy) {
1513 BOOST_CHECK(proxy.getName() ==
"also");
1516 BOOST_FAIL(
"Wrong vertex type found");
1522 BOOST_TEST(foundElements == 1);
1532 size_t foundElements = 0;
1534 auto checker = [&](
auto proxy) {
1537 BOOST_CHECK(proxy.getName() ==
"Deeper" || proxy.getName() ==
"MyModule" || proxy.getName() ==
"somepath" ||
1538 proxy.getName() ==
"Devices");
1541 BOOST_FAIL(
"Wrong vertex type found");
1545 app.
getModel().
visit(checker, ChimeraTK::Model::childDirectories);
1547 BOOST_TEST(foundElements == 4);
1566 size_t foundElements = 0;
1568 auto checker = [&](
auto proxy) {
1571 BOOST_CHECK(proxy.getName() ==
"readBack" || proxy.getName() ==
"actuator");
1574 BOOST_FAIL(
"Wrong vertex type found");
1578 dir.
visit(checker, ChimeraTK::Model::childVariables);
1580 BOOST_TEST(foundElements == 2);
1599 size_t foundElements = 0;
1601 auto checker = [&](
auto proxy) {
1604 BOOST_CHECK(proxy.getName() ==
"readBack" || proxy.getName() ==
"actuator");
1607 BOOST_CHECK(proxy.getName() ==
"pointlessVariableGroup");
1610 BOOST_FAIL(
"Wrong vertex type found");
1614 dir.
visit(checker, ChimeraTK::Model::children);
1616 BOOST_TEST(foundElements == 3);
1626 size_t foundElements = 0;
1628 auto checker = [&](
auto proxy) {
1631 BOOST_CHECK(proxy.getName() ==
"Deeper/hierarchies");
1634 BOOST_FAIL(
"Wrong vertex type found");
1640 BOOST_TEST(foundElements == 1);
1650 size_t foundElements = 0;
1652 auto checker = [&](
auto proxy) {
1655 BOOST_CHECK(proxy.getName() ==
"need");
1658 BOOST_FAIL(
"Wrong vertex type found");
1664 BOOST_TEST(foundElements == 1);
1674 size_t foundElements = 0;
1676 auto checker = [&](
auto proxy) {
1679 BOOST_CHECK(proxy.getName() ==
"hierarchies");
1682 BOOST_FAIL(
"Wrong vertex type found");
1688 BOOST_TEST(foundElements == 1);
1700 [[maybe_unused]]
auto found = app.
getModel().
visitByPath(
"/Deeper/hierarchies", [&](
auto proxy) {
1707 size_t foundElements = 0;
1709 auto checker = [&](
auto proxy) {
1712 BOOST_CHECK(proxy.getName() ==
".");
1715 BOOST_CHECK(proxy.getName() ==
"Deeper/hierarchies");
1718 BOOST_FAIL(
"Wrong vertex type found");
1722 dir.
visit(checker, ChimeraTK::Model::neighbourModules);
1724 BOOST_TEST(foundElements == 2);
1741 BOOST_TEST(rv.
getName() ==
"Deeper/hierarchies");
1756 BOOST_TEST(rv.
getName() ==
".");
1771 BOOST_TEST(rv.
getName() ==
"pointlessVariableGroup");
1782 ChimeraTK::Model::returnProcessVariable, ChimeraTK::Model::ownedVariables,
1786 BOOST_TEST(rv.
getName() ==
"tests");
1797 ChimeraTK::Model::returnDirectory, ChimeraTK::Model::getNeighbourDirectory,
1801 BOOST_TEST(rv.
getName() ==
"need");
1810 constexpr std::string_view illegalCharsToTest =
"-~!@#$%^&*()-=+{}|[]\\;':\",.<>?` ";
1812 for(
auto c : illegalCharsToTest) {
1813 std::string nameToTest =
"MyModule" + std::string(1, c) +
"withIllegalChar";
1815 (app.
myModule =
MyModule(&app, nameToTest,
"ApplicationModule directly owned by app")), ctk::logic_error);
1828 const std::unordered_set<std::string>& tags = {})
1853 BOOST_TEST(rv.
getName() ==
"trigger");
Model::RootProxy getModel()
Return the root of the application model.
void shutdown() override
This will remove the global pointer to the instance and allows creating another instance afterwards.
ApplicationModule()=default
Default constructor: Allows late initialisation of modules (e.g.
ChimeraTK::Model::ApplicationModuleProxy getModel()
Return the application model proxy representing this module.
Model::DeviceModuleProxy getModel()
void addTag(const std::string &tag)
Add a tag.
Model::ProcessVariableProxy getModel() const
ApplicationModule & getApplicationModule() const
Return the actual ApplicationModule.
const std::string & getName() const
Get the name of the ApplicationModule.
ProcessVariableProxy getTrigger() const
Get the ProcessVariableProxy for the trigger.
const std::string & getAliasOrCdd() const
Get the alias or CDD of the device.
const std::string & getName() const
Get the name of the Directory.
const std::string & getName() const
Get the name of the ModuleGroup.
ModuleGroup & getModuleGroup() const
Return the actual ModuleGroup.
const std::vector< std::shared_ptr< VariableNetworkNode > > & getNodes() const
Return all VariableNetworkNodes for this variable.
const std::string & getName() const
Get the name of the ProcessVariable.
bool visitByPath(std::string_view path, VISITOR visitor) const
Resolve the given path and call the visitor for the found object.
bool isValid() const
Check if the model is valid.
auto visit(VISITOR visitor, Args... args) const
Traverse the model using the specified filter and call the visitor functor for each ModuleGroup,...
std::string getFullyQualifiedPath() const
Return the fully qualified path.
Proxy representing the root of the application model.
void writeGraphViz(const std::string &filename, Args... args) const
Implementations of RootProxy.
bool visitByPath(std::string_view path, VISITOR visitor) const
Resolve the given path and call the visitor for the found object.
const std::string & getName() const
Get the name of the VariableGroup.
VariableGroup & getVariableGroup() const
Return the actual VariableGroup.
ChimeraTK::Model::ModuleGroupProxy getModel()
Return the application model proxy representing this module.
Helper class to set the DMAP file path.
ChimeraTK::Model::VariableGroupProxy getModel()
Return the application model proxy representing this module.
constexpr ReturnFirstHitWithValue< void > returnFirstHit()
Stop the search after the first hit and return.
constexpr bool isDirectory(const PROPERTY_OR_PROXY &)
constexpr bool isVariableGroup(const PROPERTY_OR_PROXY &)
constexpr bool isApplicationModule(const PROPERTY_OR_PROXY &)
constexpr bool isDeviceModule(const PROPERTY_OR_PROXY &)
constexpr bool isModuleGroup(const PROPERTY_OR_PROXY &)
constexpr bool hasName(const PROPERTY_OR_PROXY &)
constexpr bool isRoot(const PROPERTY_OR_PROXY &)
Predicates to identify the type of a proxy or a properties struct.
constexpr bool isVariable(const PROPERTY_OR_PROXY &)
InvalidityTracer application module.
BOOST_AUTO_TEST_CASE(testGraphViz)
This is used to allow default construction of the std::variant.
Convenience class for output scalar accessors (always UpdateMode::push)
bool operator<(const Item &rhs) const
const std::type_info & type
ctk::ScalarPollInput< int > readBack
MyModule(ctk::ModuleGroup *owner, const std::string &name, const std::string &description, const std::unordered_set< std::string > &tags={})
ctk::ScalarOutput< int > actuator
Tests::testApplicationPVModel::MyModule::PointlessVariableGroup pointlessVariableGroup
void mainLoop() override
To be implemented by the user: function called in a separate thread executing the main loop of the mo...
void mainLoop() override
To be implemented by the user: function called in a separate thread executing the main loop of the mo...
ctk::ScalarPushInput< int > var
RogueModule(ctk::ModuleGroup *owner, const std::string &name, const std::string &description, const std::unordered_set< std::string > &tags={})
~TestApplication2() override
ctk::SetDMapFilePath dmap
ctk::SetDMapFilePath dmap
~TestApplication() override
TestModuleGroup deeperHierarchies
ctk::ScalarPollInput< int > tests
void mainLoop() override
To be implemented by the user: function called in a separate thread executing the main loop of the mo...
Tests::testApplicationPVModel::TestModule::Need need
ctk::ScalarPushInput< int > also