PODIO v00-16-03
An Event-Data-Model Toolkit for High Energy Physics Experiments
Loading...
Searching...
No Matches
unittest.cpp File Reference
#include <cstdint>
#include <map>
#include <stdexcept>
#include <thread>
#include <type_traits>
#include <vector>
#include "catch2/catch_test_macros.hpp"
#include "podio/EventStore.h"
#include "podio/GenericParameters.h"
#include "podio/ROOTFrameReader.h"
#include "podio/ROOTLegacyReader.h"
#include "podio/ROOTReader.h"
#include "podio/podioVersion.h"
#include "datamodel/EventInfoCollection.h"
#include "datamodel/ExampleClusterCollection.h"
#include "datamodel/ExampleForCyclicDependency1Collection.h"
#include "datamodel/ExampleForCyclicDependency2Collection.h"
#include "datamodel/ExampleHitCollection.h"
#include "datamodel/ExampleWithOneRelationCollection.h"
#include "datamodel/ExampleWithUserInitCollection.h"
#include "datamodel/ExampleWithVectorMemberCollection.h"
#include "datamodel/MutableExampleWithComponent.h"
#include "podio/UserDataCollection.h"

Go to the source code of this file.

Typedefs

template<typename T >
using GPGetValue = decltype(std::declval< podio::GenericParameters >().getValue< T >(std::declval< std::string >()))
 

Functions

 TEST_CASE ("AutoDelete", "[basics][memory-management]")
 
 TEST_CASE ("Basics", "[basics][memory-management]")
 
 TEST_CASE ("Assignment-operator ref count", "[basics][memory-management]")
 
 TEST_CASE ("Clearing", "[ASAN-FAIL][THREAD-FAIL][basics][memory-management]")
 
 TEST_CASE ("Cloning", "[basics][memory-management]")
 
 TEST_CASE ("Component", "[basics]")
 
 TEST_CASE ("Cyclic", "[LEAK-FAIL][basics][relations][memory-management]")
 
 TEST_CASE ("Invalid_refs", "[LEAK-FAIL][basics][relations]")
 
 TEST_CASE ("Looping", "[basics]")
 
 TEST_CASE ("Notebook", "[basics]")
 
 TEST_CASE ("OneToOneRelations", "[basics][relations]")
 
 TEST_CASE ("Podness", "[basics][code-gen]")
 
 TEST_CASE ("Referencing", "[basics][relations]")
 
 TEST_CASE ("VariadicCreate", "[basics]")
 
 TEST_CASE ("write_buffer", "[basics][io]")
 
 TEST_CASE ("thread-safe prepareForWrite", "[basics][multithread]")
 
 TEST_CASE ("Extracode", "[basics][code-gen]")
 
 TEST_CASE ("AssociativeContainer", "[basics]")
 
 TEST_CASE ("Equality", "[basics]")
 
 TEST_CASE ("UserInitialization", "[basics][code-gen]")
 
 TEST_CASE ("NonPresentCollection", "[basics][event-store]")
 
 TEST_CASE ("const correct indexed access to const collections", "[const-correctness]")
 
 TEST_CASE ("const correct indexed access to collections", "[const-correctness]")
 
 TEST_CASE ("const correct iterators on const collections", "[const-correctness]")
 
 TEST_CASE ("const correct iterators on collections", "[const-correctness]")
 
 TEST_CASE ("Subset collection basics", "[subset-colls]")
 
 TEST_CASE ("Subset collection can handle subsets", "[subset-colls]")
 
 TEST_CASE ("Collection iterators work with subset collections", "[LEAK-FAIL][subset-colls]")
 
 TEST_CASE ("Canont convert a normal collection into a subset collection", "[subset-colls]")
 
 TEST_CASE ("Cannot convert a subset collection into a normal collection", "[subset-colls]")
 
 TEST_CASE ("Subset collection only handles tracked objects", "[subset-colls]")
 
auto createCollections (const size_t nElements=3u)
 
void checkCollections (ExampleHitCollection &hits, ExampleClusterCollection &clusters, ExampleWithVectorMemberCollection &vectors, podio::UserDataCollection< float > &userData, const size_t nElements=3u)
 
 TEST_CASE ("Move-only collections", "[collections][move-semantics]")
 
 TEST_CASE ("Version tests", "[versioning]")
 
 TEST_CASE ("Preprocessor version tests", "[versioning]")
 
 TEST_CASE ("GenericParameters", "[generic-parameters]")
 
 TEST_CASE ("GenericParameters constructors", "[generic-parameters]")
 
 TEST_CASE ("GenericParameters return types", "[generic-parameters][static-checks]")
 
 TEST_CASE ("Missing files (ROOT readers)", "[basics]")
 

Typedef Documentation

◆ GPGetValue

template<typename T >
using GPGetValue = decltype(std::declval<podio::GenericParameters>().getValue<T>(std::declval<std::string>()))

Definition at line 1037 of file unittest.cpp.

Function Documentation

◆ checkCollections()

void checkCollections ( ExampleHitCollection &  hits,
ExampleClusterCollection &  clusters,
ExampleWithVectorMemberCollection &  vectors,
podio::UserDataCollection< float > &  userData,
const size_t  nElements = 3u 
)

Definition at line 643 of file unittest.cpp.

645 {
646 // Basics
647 REQUIRE(hits.size() == nElements);
648 REQUIRE(clusters.size() == nElements);
649 REQUIRE(vectors.size() == nElements);
650 REQUIRE(userData.size() == nElements);
651
652 int i = 0;
653 for (auto cluster : clusters) {
654 REQUIRE(cluster.Hits(0) == hits[i++]);
655 }
656
657 i = 0;
658 for (const auto vec : vectors) {
659 const auto counts = vec.count();
660 REQUIRE(counts.size() == 2);
661 REQUIRE(counts[0] == i);
662 REQUIRE(counts[1] == i + 42);
663 i++;
664 }
665
666 i = 0;
667 for (const auto v : userData) {
668 REQUIRE(v == 3.14f * i++);
669 }
670
671 // Also check that the buffers we get are valid and have the expected contents
672 hits.prepareForWrite();
673 auto hitBuffers = hits.getBuffers();
674 if (!hits.isSubsetCollection()) {
675 auto* hitPODBuffers = hitBuffers.dataAsVector<ExampleHitData>();
676 REQUIRE(hitPODBuffers->size() == nElements);
677 for (size_t iHit = 0; iHit < nElements; ++iHit) {
678 const auto& hitPOD = (*hitPODBuffers)[iHit];
679 REQUIRE(hitPOD.cellID == static_cast<unsigned long long>(iHit));
680 REQUIRE(hitPOD.energy == 100.f * iHit);
681 }
682 }
683
684 clusters.prepareForWrite();
685 auto clusterBuffers = clusters.getBuffers();
686 auto* clusterRelationBuffers = clusterBuffers.references;
687
688 if (!clusters.isSubsetCollection()) {
689 REQUIRE(clusterRelationBuffers->size() == 2); // We have two relations, to hits and to clusters
690 const auto& hitRelationBuffer = (*clusterRelationBuffers)[0]; // Index is an implementation detail
691 REQUIRE(hitRelationBuffer->size() == nElements * 1); // Each cluster has one hit in these tests
692 for (size_t iHit = 0; iHit < nElements * 1; ++iHit) {
693 const auto& hitID = (*hitRelationBuffer)[iHit];
694 REQUIRE(hitID.index == (int)iHit);
695 REQUIRE(static_cast<unsigned>(hitID.collectionID) == hits.getID());
696 }
697 }
698
699 vectors.prepareForWrite();
700 auto vecMemBuffers = vectors.getBuffers();
701 if (!vectors.isSubsetCollection()) {
702 auto* vecMemVecBuffers = vecMemBuffers.vectorMembers;
703 REQUIRE(vecMemVecBuffers->size() == 1); // Only one vector member here
704 // Now we are really descending into implementation details
705 const auto* countBuffer = *static_cast<std::vector<int>**>((*vecMemVecBuffers)[0].second);
706 REQUIRE(countBuffer->size() == nElements * 2);
707 for (int iC = 0; iC < (int)nElements; ++iC) {
708 REQUIRE((*countBuffer)[iC * 2] == iC);
709 REQUIRE((*countBuffer)[iC * 2 + 1] == 42 + iC);
710 }
711 }
712}
size_t size() const override
number of elements in the collection

Referenced by TEST_CASE().

◆ createCollections()

auto createCollections ( const size_t  nElements = 3u)

Definition at line 608 of file unittest.cpp.

608 {
609 auto colls = std::make_tuple(ExampleHitCollection(), ExampleClusterCollection(), ExampleWithVectorMemberCollection(),
611 auto& [hitColl, clusterColl, vecMemColl, userDataColl] = colls;
612
613 for (auto i = 0u; i < nElements; ++i) {
614 auto hit = hitColl.create();
615 hit.cellID(i);
616 hit.energy(100.f * i);
617 auto cluster = clusterColl.create();
618 // create a few relations as well
619 cluster.addHits(hit);
620
621 auto vecMem = vecMemColl.create();
622 vecMem.addcount(i);
623 vecMem.addcount(42 + i);
624
625 userDataColl.push_back(3.14f * i);
626 }
627
628 vecMemColl.prepareForWrite();
629 auto buffers = vecMemColl.getBuffers();
630 auto vecBuffers = buffers.vectorMembers;
631 auto thisVec = (*vecBuffers)[0].second;
632
633 // const auto floatVec = podio::CollectionWriteBuffers::asVector<float>(thisVec);
634 const auto floatVec2 = podio::CollectionReadBuffers::asVector<float>(thisVec);
635
636 // std::cout << floatVec->size() << '\n';
637 std::cout << "** " << floatVec2->size() << " vs " << vecMemColl.size() << '\n';
638
639 return colls;
640}

Referenced by TEST_CASE().

◆ TEST_CASE() [1/38]

TEST_CASE ( "Assignment-operator ref count"  ,
""  [basics][memory-management] 
)

Definition at line 60 of file unittest.cpp.

60 {
61 // Make sure that the assignment operator handles the reference count
62 // correctly. (Will trigger in an ASan build if it is not the case)
63 // See https://github.com/AIDASoft/podio/issues/200
64 std::map<int, ExampleHit> hitMap;
65 for (int i = 0; i < 10; ++i) {
66 auto hit = ExampleHit(0x42ULL, i, i, i, i);
67 hitMap[i] = hit;
68 }
69
70 // hits should still be valid here
71 for (int i = 0; i < 10; ++i) {
72 const auto hit = hitMap[i];
73 REQUIRE(hit.energy() == i);
74 }
75}

◆ TEST_CASE() [2/38]

TEST_CASE ( "AssociativeContainer"  ,
""  [basics] 
)

Definition at line 350 of file unittest.cpp.

350 {
351 auto clu1 = ExampleCluster();
352 auto clu2 = ExampleCluster();
353 auto clu3 = ExampleCluster();
354 auto clu4 = ExampleCluster();
355 auto clu5 = ExampleCluster();
356
357 std::set<ExampleCluster> cSet;
358 cSet.insert(clu1);
359 cSet.insert(clu2);
360 cSet.insert(clu3);
361 cSet.insert(clu4);
362 cSet.insert(clu5);
363 cSet.insert(clu1);
364 cSet.insert(clu2);
365 cSet.insert(clu3);
366 cSet.insert(clu4);
367 cSet.insert(clu5);
368
369 REQUIRE(cSet.size() == 5);
370
371 std::map<ExampleCluster, int> cMap;
372 cMap[clu1] = 1;
373 cMap[clu2] = 2;
374 cMap[clu3] = 3;
375 cMap[clu4] = 4;
376 cMap[clu5] = 5;
377
378 REQUIRE(cMap[clu3] == 3);
379
380 cMap[clu3] = 42;
381
382 REQUIRE(cMap[clu3] == 42);
383}

◆ TEST_CASE() [3/38]

TEST_CASE ( "AutoDelete"  ,
""  [basics][memory-management] 
)

Definition at line 36 of file unittest.cpp.

36 {
37 auto store = podio::EventStore();
38 auto hit1 = MutableEventInfo();
39 auto hit2 = MutableEventInfo();
40 auto hit3 = MutableEventInfo();
41 auto& coll = store.create<EventInfoCollection>("info");
42 coll.push_back(hit1);
43 hit3 = hit2;
44}

◆ TEST_CASE() [4/38]

TEST_CASE ( "Basics"  ,
""  [basics][memory-management] 
)

Definition at line 46 of file unittest.cpp.

46 {
47 auto store = podio::EventStore();
48 // Adding
49 auto& collection = store.create<ExampleHitCollection>("name");
50 auto hit1 = collection.create(0xcaffeeULL, 0., 0., 0., 0.); // initialize w/ value
51 auto hit2 = collection.create(); // default initialize
52 hit2.energy(12.5);
53 // Retrieving
54 const ExampleHitCollection* coll2(nullptr);
55 REQUIRE(store.get("name", coll2));
56 const ExampleHitCollection* coll3(nullptr);
57 REQUIRE_FALSE(store.get("wrongName", coll3));
58}

◆ TEST_CASE() [5/38]

TEST_CASE ( "Cannot convert a subset collection into a normal collection"  ,
""  [subset-colls] 
)

Definition at line 587 of file unittest.cpp.

587 {
588 auto clusterRefs = ExampleClusterCollection();
589 clusterRefs.setSubsetCollection();
590
591 auto clusters = ExampleClusterCollection();
592 auto cluster = clusters.create();
593 clusterRefs.push_back(cluster);
594
595 REQUIRE_THROWS_AS(clusterRefs.setSubsetCollection(false), std::logic_error);
596}

◆ TEST_CASE() [6/38]

TEST_CASE ( "Canont convert a normal collection into a subset collection"  ,
""  [subset-colls] 
)

Definition at line 580 of file unittest.cpp.

580 {
581 auto clusterRefs = ExampleClusterCollection();
582 auto cluster = clusterRefs.create();
583
584 REQUIRE_THROWS_AS(clusterRefs.setSubsetCollection(), std::logic_error);
585}

◆ TEST_CASE() [7/38]

TEST_CASE ( "Clearing"  ,
""  [ASAN-FAIL][THREAD-FAIL][basics][memory-management] 
)

Definition at line 77 of file unittest.cpp.

77 {
78 bool success = true;
79 auto store = podio::EventStore();
80 auto& hits = store.create<ExampleHitCollection>("hits");
81 auto& clusters = store.create<ExampleClusterCollection>("clusters");
82 auto& oneRels = store.create<ExampleWithOneRelationCollection>("OneRelation");
83 auto nevents = unsigned(1000);
84 for (unsigned i = 0; i < nevents; ++i) {
85 hits.clear();
86 clusters.clear();
87 auto hit1 = hits.create();
88 auto hit2 = ExampleHit();
89 hit1.energy(double(i));
90 auto cluster = clusters.create();
91 cluster.addHits(hit1);
92 cluster.addHits(hit2);
93 hits.push_back(hit2);
94 auto oneRel = MutableExampleWithOneRelation();
95 oneRel.cluster(cluster);
96 oneRel.cluster(cluster);
97 oneRels.push_back(oneRel);
98 }
99 hits.clear();
100 if (hits.size() != 0) {
101 success = false;
102 }
103 REQUIRE(success);
104}

◆ TEST_CASE() [8/38]

TEST_CASE ( "Cloning"  ,
""  [basics][memory-management] 
)

Definition at line 106 of file unittest.cpp.

106 {
107 bool success = true;
108 auto hit = MutableExampleHit();
109 hit.energy(30);
110 auto hit2 = hit.clone();
111 hit2.energy(20);
112 if (hit.energy() == hit2.energy()) {
113 success = false;
114 }
115 auto cluster = MutableExampleCluster();
116 cluster.addHits(hit);
117 auto cluster2 = cluster.clone();
118 cluster.addHits(hit2);
119 // check that the clone of a const object is mutable
120 auto const_hit = ExampleHit();
121 auto const_hit_clone = const_hit.clone();
122 const_hit_clone.energy(30);
123 REQUIRE(success);
124}

◆ TEST_CASE() [9/38]

TEST_CASE ( "Collection iterators work with subset collections"  ,
""  [LEAK-FAIL][subset-colls] 
)

Definition at line 557 of file unittest.cpp.

557 {
558 auto hits = ExampleHitCollection();
559 auto hit1 = hits.create(0x42ULL, 0., 0., 0., 0.);
560 auto hit2 = hits.create(0x42ULL, 1., 1., 1., 1.);
561
562 auto hitRefs = ExampleHitCollection();
563 hitRefs.setSubsetCollection();
564 for (const auto h : hits) {
565 hitRefs.push_back(h);
566 }
567
568 // index-based looping / access
569 for (size_t i = 0; i < hitRefs.size(); ++i) {
570 REQUIRE(hitRefs[i].energy() == i);
571 }
572
573 // range-based for loop
574 int index = 0;
575 for (const auto h : hitRefs) {
576 REQUIRE(h.energy() == index++);
577 }
578}

◆ TEST_CASE() [10/38]

TEST_CASE ( "Component"  ,
""  [basics] 
)

Definition at line 126 of file unittest.cpp.

126 {
127 auto info = MutableExampleWithComponent();
128 info.component().data.x = 3;
129 REQUIRE(3 == info.component().data.x);
130}

◆ TEST_CASE() [11/38]

TEST_CASE ( "const correct indexed access to collections"  ,
""  [const -correctness] 
)

Definition at line 435 of file unittest.cpp.

435 {
436 auto store = podio::EventStore();
437 auto& collection = store.create<ExampleHitCollection>("irrelevant name");
438
439 STATIC_REQUIRE(std::is_same_v<decltype(collection), ExampleHitCollection&>); // collection created by store should not
440 // be const
441
442 STATIC_REQUIRE(std::is_same_v<decltype(collection[0]), MutableExampleHit>); // non-const collections should have
443 // indexed access to mutable objects
444
445 STATIC_REQUIRE(std::is_same_v<decltype(std::declval<ExampleClusterCollection>()[0]),
446 MutableExampleCluster>); // collections should have indexed access to mutable objects
447
448 STATIC_REQUIRE(std::is_same_v<decltype(std::declval<ExampleClusterCollection>().at(0)),
449 MutableExampleCluster>); // collections should have indexed access to mutable objects
450}

◆ TEST_CASE() [12/38]

TEST_CASE ( "const correct indexed access to const collections"  ,
""  [const -correctness] 
)

Definition at line 426 of file unittest.cpp.

426 {
427 STATIC_REQUIRE(std::is_same_v<decltype(std::declval<const ExampleClusterCollection>()[0]),
428 ExampleCluster>); // const collections should only have indexed access to mutable
429 // objects
430 STATIC_REQUIRE(std::is_same_v<decltype(std::declval<const ExampleClusterCollection>().at(0)),
431 ExampleCluster>); // const collections should only have indexed access to mutable
432 // objects
433}

◆ TEST_CASE() [13/38]

TEST_CASE ( "const correct iterators on collections"  ,
""  [const -correctness] 
)

Definition at line 478 of file unittest.cpp.

478 {
479 auto collection = ExampleClusterCollection();
480 for (auto cluster : collection) {
481 STATIC_REQUIRE(std::is_same_v<decltype(cluster), MutableExampleCluster>); // collection iterators should return
482 // mutable objects
483 cluster.energy(42); // this will necessarily also compile
484 }
485
486 // check the individual steps again from above, to see where things fail if they fail
487 STATIC_REQUIRE(std::is_same_v<decltype(std::declval<ExampleClusterCollection>().end()),
488 ExampleClusterMutableCollectionIterator>); // non const collection end() should return a
489 // MutableCollectionIterator
490
491 STATIC_REQUIRE(std::is_same_v<decltype(std::declval<ExampleClusterCollection>().end()),
492 ExampleClusterMutableCollectionIterator>); // non const collection end() should return a
493 // MutableCollectionIterator
494
495 STATIC_REQUIRE(std::is_same_v<decltype(std::declval<ExampleClusterCollection>().end()),
496 ExampleClusterMutableCollectionIterator>); // collection end() should return a
497 // MutableCollectionIterator
498
499 STATIC_REQUIRE(std::is_same_v<decltype(*std::declval<ExampleClusterCollection>().begin()),
500 MutableExampleCluster>); // MutableCollectionIterator should give access to mutable
501 // objects
502
503 STATIC_REQUIRE(std::is_same_v<decltype(std::declval<ExampleClusterMutableCollectionIterator>().operator->()),
504 MutableExampleCluster*>); // CollectionIterator should only give access to mutable
505 // objects
506}

◆ TEST_CASE() [14/38]

TEST_CASE ( "const correct iterators on const collections"  ,
""  [const -correctness] 
)

Definition at line 452 of file unittest.cpp.

452 {
453 const auto collection = ExampleHitCollection();
454 // this essentially checks the whole "chain" from begin() / end() through
455 // iterator operators
456 for (auto hit : collection) {
457 STATIC_REQUIRE(std::is_same_v<decltype(hit), ExampleHit>); // const collection iterators should only return
458 // immutable objects
459 }
460
461 // but we can exercise it in a detailed fashion as well to make it easier to
462 // spot where things fail, should they fail
463 STATIC_REQUIRE(std::is_same_v<decltype(std::declval<const ExampleHitCollection>().begin()),
464 ExampleHitCollectionIterator>); // const collection begin() should return a
465 // CollectionIterator
466
467 STATIC_REQUIRE(std::is_same_v<decltype(std::declval<const ExampleHitCollection>().end()),
468 ExampleHitCollectionIterator>); // const collection end() should return a
469 // CollectionIterator
470
471 STATIC_REQUIRE(std::is_same_v<decltype(*std::declval<const ExampleHitCollection>().begin()),
472 ExampleHit>); // CollectionIterator should only give access to immutable objects
473
474 STATIC_REQUIRE(std::is_same_v<decltype(std::declval<ExampleHitCollectionIterator>().operator->()),
475 ExampleHit*>); // CollectionIterator should only give access to immutable objects
476}

◆ TEST_CASE() [15/38]

TEST_CASE ( "Cyclic"  ,
""  [LEAK-FAIL][basics][relations][memory-management] 
)

Definition at line 132 of file unittest.cpp.

132 {
133 auto start = MutableExampleForCyclicDependency1();
134 auto isAvailable = start.ref().isAvailable();
135 REQUIRE_FALSE(isAvailable);
136 auto end = MutableExampleForCyclicDependency2();
137 start.ref(end);
138 isAvailable = start.ref().isAvailable();
139 REQUIRE(isAvailable);
140 end.ref(start);
141 REQUIRE(start == end.ref());
142 auto end_eq = start.ref();
143 auto start_eq = end_eq.ref();
144 REQUIRE(start == start_eq);
145 REQUIRE(start == start.ref().ref());
146}

◆ TEST_CASE() [16/38]

TEST_CASE ( "Equality"  ,
""  [basics] 
)

Definition at line 385 of file unittest.cpp.

385 {
386 auto cluster = ExampleCluster();
387 auto rel = MutableExampleWithOneRelation();
388 rel.cluster(cluster);
389 auto returned_cluster = rel.cluster();
390 REQUIRE(cluster == returned_cluster);
391 REQUIRE(returned_cluster == cluster);
392}

◆ TEST_CASE() [17/38]

TEST_CASE ( "Extracode"  ,
""  [basics][code-gen] 
)

Definition at line 338 of file unittest.cpp.

338 {
339 auto ev = MutableEventInfo();
340 ev.setNumber(42);
341 REQUIRE(ev.getNumber() == 42);
342
343 int ia[3] = {1, 2, 3};
344 auto simple = SimpleStruct(ia);
345 REQUIRE(simple.x == 1);
346 REQUIRE(simple.y == 2);
347 REQUIRE(simple.z == 3);
348}

◆ TEST_CASE() [18/38]

TEST_CASE ( "GenericParameters constructors"  ,
""  [generic-parameters] 
)

Definition at line 992 of file unittest.cpp.

992 {
993 // Tests for making sure that generic parameters can be moved / copied correctly
994 auto originalParams = podio::GenericParameters{};
995 originalParams.setValue("int", 42);
996 originalParams.setValue("ints", {1, 2});
997 originalParams.setValue("float", 3.14f);
998 originalParams.setValue("double", 2 * 3.14);
999 originalParams.setValue("strings", {"one", "two", "three"});
1000
1001 SECTION("Copy constructor") {
1002 auto copiedParams = originalParams;
1003 REQUIRE(copiedParams.getValue<int>("int") == 42);
1004 REQUIRE(copiedParams.getValue<std::vector<int>>("ints")[1] == 2);
1005 REQUIRE(copiedParams.getValue<float>("float") == 3.14f);
1006 REQUIRE(copiedParams.getValue<double>("double") == 2 * 3.14);
1007 REQUIRE(copiedParams.getValue<std::vector<std::string>>("strings")[0] == "one");
1008
1009 // Make sure these are truly independent copies now
1010 copiedParams.setValue("anotherDouble", 1.2345);
1011 REQUIRE(originalParams.getValue<double>("anotherDouble") == double{});
1012 }
1013
1014 SECTION("Move constructor") {
1015 auto copiedParams = std::move(originalParams);
1016 REQUIRE(copiedParams.getValue<int>("int") == 42);
1017 REQUIRE(copiedParams.getValue<std::vector<int>>("ints")[1] == 2);
1018 REQUIRE(copiedParams.getValue<float>("float") == 3.14f);
1019 REQUIRE(copiedParams.getValue<double>("double") == 2 * 3.14);
1020 REQUIRE(copiedParams.getValue<std::vector<std::string>>("strings")[0] == "one");
1021 }
1022
1023 SECTION("Move assignment") {
1024 auto copiedParams = podio::GenericParameters{};
1025 copiedParams = std::move(originalParams);
1026 REQUIRE(copiedParams.getValue<int>("int") == 42);
1027 REQUIRE(copiedParams.getValue<std::vector<int>>("ints")[1] == 2);
1028 REQUIRE(copiedParams.getValue<float>("float") == 3.14f);
1029 REQUIRE(copiedParams.getValue<double>("double") == 2 * 3.14);
1030 REQUIRE(copiedParams.getValue<std::vector<std::string>>("strings")[0] == "one");
1031 }
1032}
void setValue(const std::string &key, T value)
Store (a copy of) the passed value under the given key.

◆ TEST_CASE() [19/38]

TEST_CASE ( "GenericParameters return types"  ,
""  [generic-parameters][static-checks] 
)

Definition at line 1039 of file unittest.cpp.

1039 {
1040 // Tests for checking that the getValue returns return by value resp. by const
1041 // reference as expected
1042 STATIC_REQUIRE(std::is_same_v<GPGetValue<int>, int>); // int and float are returned by value
1043 STATIC_REQUIRE(std::is_same_v<GPGetValue<std::vector<int>>, const std::vector<int>&>); // vectors are const
1044 // references
1045
1046 STATIC_REQUIRE(std::is_same_v<GPGetValue<std::string>, const std::string&>); // std::strings are returned by const
1047 // reference as well
1048 STATIC_REQUIRE(std::is_same_v<GPGetValue<std::vector<std::string>>, const std::vector<std::string>&>); // as are
1049 // vectors of
1050 // strings
1051}
decltype(std::declval< podio::GenericParameters >().getValue< T >(std::declval< std::string >())) GPGetValue
Definition: unittest.cpp:1037

◆ TEST_CASE() [20/38]

TEST_CASE ( "GenericParameters"  ,
""  [generic-parameters] 
)

Definition at line 925 of file unittest.cpp.

925 {
926 // Check that GenericParameters work as intended
927 auto gp = podio::GenericParameters{};
928
929 gp.setValue("anInt", 42);
930 REQUIRE(gp.getValue<int>("anInt") == 42);
931 // Make sure that resetting a value with the same key works
932 gp.setValue("anInt", -42);
933 REQUIRE(gp.getValue<int>("anInt") == -42);
934
935 // Make sure that passing a string literal is converted to a string on the fly
936 gp.setValue("aString", "const char initialized");
937 REQUIRE(gp.getValue<std::string>("aString") == "const char initialized");
938
939 gp.setValue("aStringVec", {"init", "from", "const", "chars"});
940 const auto& stringVec = gp.getValue<std::vector<std::string>>("aStringVec");
941 REQUIRE(stringVec.size() == 4);
942 REQUIRE(stringVec[0] == "init");
943 REQUIRE(stringVec[3] == "chars");
944
945 // Check that storing double values works
946 gp.setValue("double", 1.234);
947 gp.setValue("manyDoubles", {1.23, 4.56, 7.89});
948 REQUIRE(gp.getValue<double>("double") == 1.234);
949 const auto& storedDoubles = gp.getValue<std::vector<double>>("manyDoubles");
950 REQUIRE(storedDoubles.size() == 3);
951 REQUIRE(storedDoubles[0] == 1.23);
952 REQUIRE(storedDoubles[1] == 4.56);
953 REQUIRE(storedDoubles[2] == 7.89);
954
955 // Check that passing an initializer_list creates the vector on the fly
956 gp.setValue("manyInts", {1, 2, 3, 4});
957 const auto& ints = gp.getValue<std::vector<int>>("manyInts");
958 REQUIRE(ints.size() == 4);
959 for (int i = 0; i < 4; ++i) {
960 REQUIRE(ints[i] == i + 1);
961 }
962
963 auto floats = std::vector<float>{3.14f, 2.718f};
964 // This stores a copy of the current value
965 gp.setValue("someFloats", floats);
966 // Hence, modifying the original vector will not be reflected
967 floats.push_back(42.f);
968 REQUIRE(floats.size() == 3);
969
970 const auto& storedFloats = gp.getValue<std::vector<float>>("someFloats");
971 REQUIRE(storedFloats.size() == 2);
972 REQUIRE(storedFloats[0] == 3.14f);
973 REQUIRE(storedFloats[1] == 2.718f);
974
975 // We can at this point reset this to a single value with the same key even if
976 // it has been a vector before
977 gp.setValue("someFloats", 12.34f);
978 REQUIRE(gp.getValue<float>("someFloats") == 12.34f);
979
980 // Missing values return the default initialized ones
981 REQUIRE(gp.getValue<int>("MissingValue") == int{});
982 REQUIRE(gp.getValue<float>("MissingValue") == float{});
983 REQUIRE(gp.getValue<std::string>("MissingValue") == std::string{}); // NOLINT(readability-container-size-empty): We
984 // want the explicit comparison here
985
986 // Same for vectors
987 REQUIRE(gp.getValue<std::vector<int>>("MissingValue").empty());
988 REQUIRE(gp.getValue<std::vector<float>>("MissingValue").empty());
989 REQUIRE(gp.getValue<std::vector<std::string>>("MissingValue").empty());
990}

◆ TEST_CASE() [21/38]

TEST_CASE ( "Invalid_refs"  ,
""  [LEAK-FAIL][basics][relations] 
)

Definition at line 148 of file unittest.cpp.

148 {
149 auto store = podio::EventStore();
150 auto& hits = store.create<ExampleHitCollection>("hits");
151 auto hit1 = hits.create(0xcaffeeULL, 0., 0., 0., 0.);
152 auto hit2 = ExampleHit();
153 auto& clusters = store.create<ExampleClusterCollection>("clusters");
154 auto cluster = clusters.create();
155 cluster.addHits(hit1);
156 cluster.addHits(hit2);
157 REQUIRE_THROWS_AS(clusters.prepareForWrite(), std::runtime_error);
158}

◆ TEST_CASE() [22/38]

TEST_CASE ( "Looping"  ,
""  [basics] 
)

Definition at line 160 of file unittest.cpp.

160 {
161 auto store = podio::EventStore();
162 auto& coll = store.create<ExampleHitCollection>("name");
163 auto hit1 = coll.create(0xbadULL, 0., 0., 0., 0.);
164 auto hit2 = coll.create(0xcaffeeULL, 1., 1., 1., 1.);
165 for (auto&& i : coll) {
166 i.energy(42); // make sure that we can indeed change the energy here for
167 // non-const collections
168 }
169 REQUIRE(hit1.energy() == 42);
170 REQUIRE(hit2.energy() == 42);
171
172 for (int i = 0, end = coll.size(); i != end; ++i) {
173 coll[i].energy(i); // reset it back to the original value
174 }
175
176 REQUIRE(coll[0].energy() == 0);
177 REQUIRE(coll[1].energy() == 1);
178
179 auto& constColl = store.get<ExampleHitCollection>("name");
180 int index = 0;
181 for (auto hit : constColl) {
182 auto energy = hit.energy();
183 REQUIRE(energy == index++);
184 }
185}

◆ TEST_CASE() [23/38]

TEST_CASE ( "Missing files (ROOT readers)"  ,
""  [basics] 
)

Definition at line 1053 of file unittest.cpp.

1053 {
1054 auto root_reader = podio::ROOTReader();
1055 REQUIRE_THROWS_AS(root_reader.openFile("NonExistentFile.root"), std::runtime_error);
1056
1057 auto root_legacy_reader = podio::ROOTLegacyReader();
1058 REQUIRE_THROWS_AS(root_legacy_reader.openFile("NonExistentFile.root"), std::runtime_error);
1059
1060 auto root_frame_reader = podio::ROOTFrameReader();
1061 REQUIRE_THROWS_AS(root_frame_reader.openFile("NonExistentFile.root"), std::runtime_error);
1062}

◆ TEST_CASE() [24/38]

TEST_CASE ( "Move-only collections"  ,
""  [collections][move-semantics] 
)

Definition at line 717 of file unittest.cpp.

717 {
718 // Setup a few collections that will be used throughout below
719 auto [hitColl, clusterColl, vecMemColl, userDataColl] = createCollections();
720
721 // Hopefully redundant check for setup
722 checkCollections(hitColl, clusterColl, vecMemColl, userDataColl);
723
724 SECTION("Move constructor") {
725 // Move-construct collections and make sure the size is as expected
726 auto newHits = std::move(hitColl);
727 auto newClusters = std::move(clusterColl);
728 auto newVecMems = std::move(vecMemColl);
729 auto newUserData = std::move(userDataColl);
730
731 checkCollections(newHits, newClusters, newVecMems, newUserData);
732 }
733
734 SECTION("Move assignment") {
735 // Move assign collections and make sure everything is as expected
736 auto newHits = ExampleHitCollection();
737 newHits = std::move(hitColl);
738
739 auto newClusters = ExampleClusterCollection();
740 newClusters = std::move(clusterColl);
741
742 auto newVecMems = ExampleWithVectorMemberCollection();
743 newVecMems = std::move(vecMemColl);
744
745 auto newUserData = podio::UserDataCollection<float>();
746 newUserData = std::move(userDataColl);
747
748 checkCollections(newHits, newClusters, newVecMems, newUserData);
749 }
750
751 SECTION("Prepared collections can be move constructed") {
752 hitColl.prepareForWrite();
753 auto newHits = std::move(hitColl);
754
755 clusterColl.prepareForWrite();
756 auto newClusters = std::move(clusterColl);
757
758 vecMemColl.prepareForWrite();
759 auto buffers = vecMemColl.getBuffers();
760 auto vecBuffers = buffers.vectorMembers;
761 auto thisVec = (*vecBuffers)[0].second;
762
763 const auto floatVec = podio::CollectionWriteBuffers::asVector<float>(thisVec);
764 const auto floatVec2 = podio::CollectionReadBuffers::asVector<float>(thisVec);
765
766 std::cout << floatVec->size() << '\n';
767 std::cout << floatVec2->size() << '\n';
768
769 // auto vecBuffers = buffers.vectorMembers;
770 // const auto vecBuffer = podio::CollectionWriteBuffers::asVector<float>((*vecBuffers)[0].second);
771 // TD<decltype(vecBuffer)> td;
772 // REQUIRE(vecBuffer->size() == 2);
773 auto newVecMems = std::move(vecMemColl);
774
775 userDataColl.prepareForWrite();
776 auto newUserData = std::move(userDataColl);
777
778 checkCollections(newHits, newClusters, newVecMems, newUserData);
779 }
780
781 SECTION("Moved collections can be prepared") {
782 }
783
784 SECTION("Prepared collections can be move assigned") {
785 hitColl.prepareForWrite();
786 clusterColl.prepareForWrite();
787 vecMemColl.prepareForWrite();
788
789 auto newHits = ExampleHitCollection();
790 newHits = std::move(hitColl);
791
792 auto newClusters = ExampleClusterCollection();
793 newClusters = std::move(clusterColl);
794
795 auto newVecMems = ExampleWithVectorMemberCollection();
796 newVecMems = std::move(vecMemColl);
797
798 auto newUserData = podio::UserDataCollection<float>();
799 newUserData = std::move(userDataColl);
800
801 checkCollections(newHits, newClusters, newVecMems, newUserData);
802 }
803
804 SECTION("Subset collections can be moved") {
805 // NOTE: Does not apply to UserDataCollections!
806 auto subsetHits = ExampleHitCollection();
807 subsetHits.setSubsetCollection();
808 for (auto hit : hitColl) {
809 subsetHits.push_back(hit);
810 }
811 checkCollections(subsetHits, clusterColl, vecMemColl, userDataColl);
812
813 auto newSubsetHits = std::move(subsetHits);
814 REQUIRE(newSubsetHits.isSubsetCollection());
815 checkCollections(newSubsetHits, clusterColl, vecMemColl, userDataColl);
816
817 auto subsetClusters = ExampleClusterCollection();
818 subsetClusters.setSubsetCollection();
819 for (auto cluster : clusterColl) {
820 subsetClusters.push_back(cluster);
821 }
822 checkCollections(newSubsetHits, subsetClusters, vecMemColl, userDataColl);
823
824 // Test move-assignment here as well
825 auto newSubsetClusters = ExampleClusterCollection();
826 newSubsetClusters = std::move(subsetClusters);
827 REQUIRE(newSubsetClusters.isSubsetCollection());
828 checkCollections(newSubsetHits, newSubsetClusters, vecMemColl, userDataColl);
829
830 auto subsetVecs = ExampleWithVectorMemberCollection();
831 subsetVecs.setSubsetCollection();
832 for (auto vec : vecMemColl) {
833 subsetVecs.push_back(vec);
834 }
835 checkCollections(newSubsetHits, newSubsetClusters, subsetVecs, userDataColl);
836
837 auto newSubsetVecs = std::move(subsetVecs);
838 REQUIRE(newSubsetVecs.isSubsetCollection());
839 checkCollections(hitColl, clusterColl, newSubsetVecs, userDataColl);
840 }
841}
auto createCollections(const size_t nElements=3u)
Definition: unittest.cpp:608
void checkCollections(ExampleHitCollection &hits, ExampleClusterCollection &clusters, ExampleWithVectorMemberCollection &vectors, podio::UserDataCollection< float > &userData, const size_t nElements=3u)
Definition: unittest.cpp:643

◆ TEST_CASE() [25/38]

TEST_CASE ( "NonPresentCollection"  ,
""  [basics][event-store] 
)

Definition at line 421 of file unittest.cpp.

421 {
422 auto store = podio::EventStore();
423 REQUIRE_THROWS_AS(store.get<ExampleHitCollection>("NonPresentCollection"), std::runtime_error);
424}

◆ TEST_CASE() [26/38]

TEST_CASE ( "Notebook"  ,
""  [basics] 
)

Definition at line 187 of file unittest.cpp.

187 {
188 auto store = podio::EventStore();
189 auto& hits = store.create<ExampleHitCollection>("hits");
190 for (unsigned i = 0; i < 12; ++i) {
191 auto hit = hits.create(0xcaffeeULL, 0., 0., 0., double(i));
192 }
193
194 // Request only subset
195 auto energies = hits.energy(10);
196 REQUIRE(energies.size() == 10);
197 int index = 0;
198 for (auto energy : energies) {
199 REQUIRE(double(index) == energy);
200 ++index;
201 }
202
203 // Make sure there are no "invented" values
204 REQUIRE(hits.energy(24).size() == hits.size());
205 REQUIRE(hits.energy().size() == hits.size());
206}

◆ TEST_CASE() [27/38]

TEST_CASE ( "OneToOneRelations"  ,
""  [basics][relations] 
)

Definition at line 208 of file unittest.cpp.

208 {
209 bool success = true;
210 auto cluster = ExampleCluster();
211 auto rel = MutableExampleWithOneRelation();
212 rel.cluster(cluster);
213 REQUIRE(success);
214}

◆ TEST_CASE() [28/38]

TEST_CASE ( "Podness"  ,
""  [basics][code-gen] 
)

Definition at line 216 of file unittest.cpp.

216 {
217 // fail this already at compile time
218 STATIC_REQUIRE(std::is_standard_layout_v<ExampleClusterData>); // Generated data classes do not have standard layout
219 STATIC_REQUIRE(std::is_trivially_copyable_v<ExampleClusterData>); // Generated data classes are not trivially copyable
220 STATIC_REQUIRE(std::is_standard_layout_v<ExampleHitData>); // Generated data classes do not have standard layout
221 STATIC_REQUIRE(std::is_trivially_copyable_v<ExampleHitData>); // Generated data classes are not trivially copyable
222 STATIC_REQUIRE(std::is_standard_layout_v<ExampleWithOneRelationData>); // Generated data classes do not have standard
223 // layout
224 STATIC_REQUIRE(std::is_trivially_copyable_v<ExampleWithOneRelationData>); // Generated data classes are not trivially
225 // copyable
226}

◆ TEST_CASE() [29/38]

TEST_CASE ( "Preprocessor version tests"  ,
""  [versioning] 
)

Definition at line 883 of file unittest.cpp.

883 {
884 SECTION("Basic functionality") {
885 using namespace podio::version;
886 // Check that preprocessor comparisons work by actually invoking the
887 // preprocessor
888#if PODIO_BUILD_VERSION == PODIO_VERSION(podio_VERSION_MAJOR, podio_VERSION_MINOR, podio_VERSION_PATCH)
889 STATIC_REQUIRE(true);
890#else
891 STATIC_REQUIRE(false);
892#endif
893
894 // Make sure that we can actually decode 64 bit versions
895 STATIC_REQUIRE(decode_version(PODIO_BUILD_VERSION) == build_version);
896
897 STATIC_REQUIRE(PODIO_MAJOR_VERSION(PODIO_BUILD_VERSION) == build_version.major);
898 STATIC_REQUIRE(PODIO_MINOR_VERSION(PODIO_BUILD_VERSION) == build_version.minor);
899 STATIC_REQUIRE(PODIO_PATCH_VERSION(PODIO_BUILD_VERSION) == build_version.patch);
900
901 // Make a few checks where other versions are "maxed out"
902 STATIC_REQUIRE(PODIO_MAJOR_VERSION(PODIO_VERSION(10000, 65535, 65535)) == 10000);
903 STATIC_REQUIRE(PODIO_MINOR_VERSION(PODIO_VERSION(65535, 20000, 65535)) == 20000);
904 STATIC_REQUIRE(PODIO_PATCH_VERSION(PODIO_VERSION(65535, 65535, 30000)) == 30000);
905 }
906
907 SECTION("Comparing") {
908 // Using some large numbers here to check what happens if we start to
909 // actually use the 16 available bits
910 // patch version
911 STATIC_REQUIRE(PODIO_VERSION(10000, 20000, 39999) < PODIO_VERSION(10000, 20000, 40000));
912
913 // minor version
914 STATIC_REQUIRE(PODIO_VERSION(10000, 30000, 33333) > PODIO_VERSION(10000, 29999, 33333));
915 STATIC_REQUIRE(PODIO_VERSION(10000, 30000, 33333) < PODIO_VERSION(10000, 30001, 44444));
916
917 // major version
918 STATIC_REQUIRE(PODIO_VERSION(20000, 40000, 0) < PODIO_VERSION(20001, 40000, 0));
919 STATIC_REQUIRE(PODIO_VERSION(20000, 40000, 10000) < PODIO_VERSION(20001, 30000, 0));
920 STATIC_REQUIRE(PODIO_VERSION(20001, 40000, 10000) > PODIO_VERSION(20000, 40000, 20000));
921 STATIC_REQUIRE(PODIO_VERSION(20000, 40000, 10000) > PODIO_VERSION(19999, 50000, 30000));
922 }
923}
#define PODIO_MAJOR_VERSION(v)
Get the major version from a preprocessor defined version.
#define PODIO_VERSION(major, minor, patch)
Define a version to be used in podio.
#define PODIO_PATCH_VERSION(v)
Get the patch version from a preprocessor defined version.
#define PODIO_MINOR_VERSION(v)
Get the minor version from a preprocessor defined version.
#define PODIO_BUILD_VERSION
The encoded version with which podio has been built.

◆ TEST_CASE() [30/38]

TEST_CASE ( "Referencing"  ,
""  [basics][relations] 
)

Definition at line 228 of file unittest.cpp.

228 {
229 auto store = podio::EventStore();
230 auto& hits = store.create<ExampleHitCollection>("hits");
231 auto hit1 = hits.create(0x42ULL, 0., 0., 0., 0.);
232 auto hit2 = hits.create(0x42ULL, 1., 1., 1., 1.);
233 auto& clusters = store.create<ExampleClusterCollection>("clusters");
234 auto cluster = clusters.create();
235 cluster.addHits(hit1);
236 cluster.addHits(hit2);
237 int index = 0;
238 for (auto i = cluster.Hits_begin(), end = cluster.Hits_end(); i != end; ++i) {
239 REQUIRE(i->energy() == index);
240 ++index;
241 }
242}

◆ TEST_CASE() [31/38]

TEST_CASE ( "Subset collection basics"  ,
""  [subset-colls] 
)

Definition at line 508 of file unittest.cpp.

508 {
509 auto clusterRefs = ExampleClusterCollection();
510 clusterRefs.setSubsetCollection();
511
512 // The following will always be true
513 REQUIRE(clusterRefs.isSubsetCollection());
514 const auto refCollBuffers = clusterRefs.getBuffers();
515 REQUIRE(refCollBuffers.data == nullptr);
516 REQUIRE(refCollBuffers.vectorMembers->empty());
517 REQUIRE(refCollBuffers.references->size() == 1u);
518}

◆ TEST_CASE() [32/38]

TEST_CASE ( "Subset collection can handle subsets"  ,
""  [subset-colls] 
)

Definition at line 520 of file unittest.cpp.

520 {
521 // Can only collect things that already live in a different colection
522 auto clusters = ExampleClusterCollection();
523 auto cluster = clusters.create();
524
525 auto clusterRefs = ExampleClusterCollection();
526 clusterRefs.setSubsetCollection();
527 clusterRefs.push_back(cluster);
528
529 auto clusterRef = clusterRefs[0];
530 STATIC_REQUIRE(std::is_same_v<decltype(clusterRef), decltype(cluster)>); // Elements that can be obtained from a
531 // collection and a subset collection should
532 // have the same type
533
534 REQUIRE(clusterRef == cluster);
535
536 // These are "true" subsets, so changes should propagate
537 cluster.energy(42);
538 REQUIRE(clusterRef.energy() == 42);
539 // Also in the other directon
540 clusterRef.energy(-42);
541 REQUIRE(cluster.energy() == -42);
542
543 clusters.setID(42);
544 for (auto c : clusters) {
545 REQUIRE(c.getObjectID().collectionID == 42);
546 }
547
548 // Setting the ID on a subset collection should not change the IDs of the
549 // reference objects as otherwise we cannot use them in I/O
550 clusterRefs.setID(314);
551 REQUIRE(clusterRefs.getID() == 314);
552 for (auto c : clusterRefs) {
553 REQUIRE(c.getObjectID().collectionID == 42);
554 }
555}

◆ TEST_CASE() [33/38]

TEST_CASE ( "Subset collection only handles tracked objects"  ,
""  [subset-colls] 
)

Definition at line 598 of file unittest.cpp.

598 {
599 auto clusterRefs = ExampleClusterCollection();
600 clusterRefs.setSubsetCollection();
601 auto cluster = ExampleCluster();
602
603 REQUIRE_THROWS_AS(clusterRefs.push_back(cluster), std::invalid_argument);
604 REQUIRE_THROWS_AS(clusterRefs.create(), std::logic_error);
605}

◆ TEST_CASE() [34/38]

TEST_CASE ( "thread-safe prepareForWrite"  ,
""  [basics][multithread] 
)

Definition at line 282 of file unittest.cpp.

282 {
283 // setup a collection that we can then prepareForWrite from multiple threads
284 constexpr auto nElements = 100u;
285 ExampleHitCollection hits{};
287 for (size_t i = 0; i < nElements; ++i) {
288 hits.create(i, i * 0.5, i * 1.5, i * 2.5, 3.14);
289 userInts.push_back(i);
290 }
291
292 constexpr int nThreads = 10;
293 std::vector<std::thread> threads{};
294 threads.reserve(nThreads);
295
296 for (int i = 0; i < nThreads; ++i) {
297 threads.emplace_back([&hits, &userInts]() {
298 hits.prepareForWrite();
299 userInts.prepareForWrite();
300 });
301 }
302
303 for (auto& t : threads) {
304 t.join();
305 }
306
307 // NOTE: doing this on a single thread, because getBuffers is not threadsafe
308 auto buffers = hits.getBuffers();
309 auto* dataVec = buffers.dataAsVector<ExampleHitData>();
310 REQUIRE(dataVec->size() == nElements);
311
312 auto intBuffers = userInts.getBuffers();
313 auto* intVec = intBuffers.dataAsVector<std::uint64_t>();
314 REQUIRE(intVec->size() == nElements);
315
316 size_t i = 0;
317 for (const auto& h : *dataVec) {
318 REQUIRE(h.energy == 3.14);
319 REQUIRE(h.cellID == i);
320 REQUIRE(h.x == i * 0.5);
321 REQUIRE(h.y == i * 1.5);
322 REQUIRE(h.z == i * 2.5);
323
324 REQUIRE((*intVec)[i] == i);
325
326 i++;
327 }
328}
void push_back(const BasicType &value)

◆ TEST_CASE() [35/38]

TEST_CASE ( "UserInitialization"  ,
""  [basics][code-gen] 
)

Definition at line 394 of file unittest.cpp.

394 {
395 ExampleWithUserInitCollection coll;
396 // Default initialization values should work even through the create factory
397 auto elem = coll.create();
398 REQUIRE(elem.i16Val() == 42);
399 REQUIRE(elem.floats()[0] == 3.14f);
400 REQUIRE(elem.floats()[1] == 1.23f);
401 REQUIRE(elem.s().x == 10);
402 REQUIRE(elem.s().y == 11);
403 REQUIRE(elem.d() == 9.876e5);
404 REQUIRE(elem.comp().i == 42);
405 REQUIRE(elem.comp().arr[0] == 1.2);
406 REQUIRE(elem.comp().arr[1] == 3.4);
407
408 // And obviously when initialized directly
409 auto ex = ExampleWithUserInit{};
410 REQUIRE(ex.i16Val() == 42);
411 REQUIRE(ex.floats()[0] == 3.14f);
412 REQUIRE(ex.floats()[1] == 1.23f);
413 REQUIRE(ex.s().x == 10);
414 REQUIRE(ex.s().y == 11);
415 REQUIRE(ex.d() == 9.876e5);
416 REQUIRE(ex.comp().i == 42);
417 REQUIRE(ex.comp().arr[0] == 1.2);
418 REQUIRE(ex.comp().arr[1] == 3.4);
419}

◆ TEST_CASE() [36/38]

TEST_CASE ( "VariadicCreate"  ,
""  [basics] 
)

Definition at line 244 of file unittest.cpp.

244 {
245 // Test that objects created via the variadic create template function handle relations correctly
246 auto store = podio::EventStore();
247 auto& clusters = store.create<ExampleClusterCollection>("clusters");
248
249 auto variadic_cluster = clusters.create(3.14f);
250 auto normal_cluster = clusters.create();
251 normal_cluster.energy(42);
252
253 variadic_cluster.addClusters(normal_cluster);
254 REQUIRE(variadic_cluster.Clusters_size() == 1);
255 REQUIRE(variadic_cluster.Clusters(0) == normal_cluster);
256}

◆ TEST_CASE() [37/38]

TEST_CASE ( "Version tests"  ,
""  [versioning] 
)

Definition at line 843 of file unittest.cpp.

843 {
844 using namespace podio::version;
845 // all of these comparisons should be possible at compile time -> STATIC_REQUIRE
846
847 // major version checks
848 constexpr Version ver_1{1};
849 constexpr Version ver_2{2};
850 constexpr Version ver_1_1{1, 1};
851 constexpr Version ver_2_1{2, 1};
852 constexpr Version ver_1_1_1{1, 1, 1};
853 constexpr Version ver_1_0_2{1, 0, 2};
854 constexpr Version ver_2_0_2{2, 0, 2};
855
856 SECTION("Equality") {
857 STATIC_REQUIRE(ver_1 == Version{1, 0, 0});
858 STATIC_REQUIRE(ver_1 != ver_2);
859 STATIC_REQUIRE(ver_1_1_1 == Version{1, 1, 1});
860 STATIC_REQUIRE(ver_2_1 != ver_1_1);
861 STATIC_REQUIRE(ver_1_0_2 != ver_2_0_2);
862 }
863
864 SECTION("Major version") {
865 STATIC_REQUIRE(ver_1 < ver_2);
866 STATIC_REQUIRE(Version{3} > ver_2);
867 }
868
869 SECTION("Minor version") {
870 STATIC_REQUIRE(ver_1 < ver_1_1);
871 STATIC_REQUIRE(ver_2_1 > ver_2);
872 STATIC_REQUIRE(ver_1_1 < ver_2);
873 }
874
875 SECTION("Patch version") {
876 STATIC_REQUIRE(ver_1 < ver_1_0_2);
877 STATIC_REQUIRE(ver_1 < ver_1_1_1);
878 STATIC_REQUIRE(ver_1_1_1 > ver_1_1);
879 STATIC_REQUIRE(ver_2_0_2 < ver_2_1);
880 }
881}

◆ TEST_CASE() [38/38]

TEST_CASE ( "write_buffer"  ,
""  [basics][io] 
)

Definition at line 258 of file unittest.cpp.

258 {
259 auto store = podio::EventStore();
260 auto& coll = store.create<ExampleHitCollection>("data");
261 auto hit1 = coll.create(0x42ULL, 0., 0., 0., 0.);
262 auto hit2 = coll.create(0x42ULL, 1., 1., 1., 1.);
263 auto& clusters = store.create<ExampleClusterCollection>("clusters");
264 auto cluster = clusters.create();
265 // add a few related objects to also exercise relation writing
266 cluster.addHits(hit1);
267 cluster.addHits(hit2);
268
269 REQUIRE_NOTHROW(clusters.prepareForWrite());
270 auto buffers = clusters.getBuffers();
271 REQUIRE(buffers.dataAsVector<ExampleClusterData>()->size() == clusters.size());
272
273 // a second call should not crash the whole thing and leave everything untouched
274 REQUIRE_NOTHROW(clusters.prepareForWrite());
275 REQUIRE(clusters.getBuffers().data == buffers.data);
276
277 auto& ref_coll = store.create<ExampleWithOneRelationCollection>("onerel");
278 auto withRef = ref_coll.create();
279 REQUIRE_NOTHROW(ref_coll.prepareForWrite());
280}