File indexing completed on 2026-03-28 07:48:28
0001
0002
0003
0004
0005
0006
0007 #pragma once
0008
0009 #include <stdexcept>
0010 #include <string_view>
0011 #include <unordered_map>
0012 #include <type_traits>
0013 #include <fmt/format.h>
0014 #include <podio/CollectionBase.h>
0015 #include <podio/utilities/TypeHelpers.h>
0016
0017
0018 #include "services/io/podio/datamodel_includes.h"
0019
0020
0021
0022
0023 template <typename T> struct PodioTypeMap {
0024 using collection_t = typename T::collection_type;
0025 using mutable_t = typename T::mutable_type;
0026 };
0027
0028
0029
0030
0031
0032
0033
0034
0035
0036
0037
0038
0039
0040
0041
0042
0043
0044
0045
0046
0047
0048 template <typename Visitor> class CollectionVisitorMap {
0049 public:
0050 using FunctionType = void (*)(Visitor&, const podio::CollectionBase&);
0051
0052 private:
0053 std::unordered_map<std::string_view, FunctionType> m_map;
0054
0055 template <typename CollectionT>
0056 static void visitCollection(Visitor& visitor, const podio::CollectionBase& collection) {
0057 static_assert(std::is_base_of_v<podio::CollectionBase, CollectionT>,
0058 "CollectionT must be derived from podio::CollectionBase");
0059 visitor(*static_cast<const CollectionT*>(&collection));
0060 }
0061
0062 template <typename CollectionT> void addToMap() {
0063 m_map[CollectionT::typeName] = &visitCollection<CollectionT>;
0064 }
0065
0066 template <typename DataT> void addDataTypeToMap() { addToMap<typename DataT::collection_type>(); }
0067
0068 template <typename... DataTypes>
0069 void addAllDataCollections(podio::utils::TypeList<DataTypes...>) {
0070 (addDataTypeToMap<DataTypes>(), ...);
0071 }
0072
0073 template <typename... LinkTypes>
0074 void addAllLinkCollections(podio::utils::TypeList<LinkTypes...>) {
0075 (addDataTypeToMap<LinkTypes>(), ...);
0076 }
0077
0078 public:
0079 CollectionVisitorMap() {
0080
0081 addAllDataCollections(typename edm4hep::edm4hepDataTypes{});
0082 addAllDataCollections(typename edm4eic::edm4eicDataTypes{});
0083
0084
0085 addAllLinkCollections(typename edm4hep::edm4hepLinkTypes{});
0086 addAllLinkCollections(typename edm4eic::edm4eicLinkTypes{});
0087 }
0088
0089 const auto& getMap() const { return m_map; }
0090 };
0091
0092
0093
0094
0095
0096
0097
0098
0099
0100
0101
0102
0103
0104
0105
0106
0107
0108
0109
0110
0111
0112
0113
0114
0115
0116
0117
0118
0119
0120
0121
0122
0123 template <typename Visitor> struct VisitPodioCollection {
0124 void operator()(Visitor& visitor, const podio::CollectionBase& collection) {
0125
0126 static const CollectionVisitorMap<Visitor> visitorMap;
0127
0128 auto typeName = collection.getTypeName();
0129 auto it = visitorMap.getMap().find(typeName);
0130
0131 if (it != visitorMap.getMap().end()) {
0132 it->second(visitor, collection);
0133 } else {
0134 throw std::runtime_error(fmt::format(
0135 "Unrecognized podio typename: {}.\n"
0136 "This type was not found in the supported datamodels (EDM4hep, EDM4eic).\n"
0137 "Possible causes:\n"
0138 " - The type is not defined in EDM4hep or EDM4eic datamodels.\n"
0139 " - You may be using an incompatible or outdated version of the datamodels.\n"
0140 " - There may be a typo in the type name.\n"
0141 "Please check your datamodel installation and ensure you are using compatible versions.",
0142 typeName));
0143 }
0144 }
0145 };