7#include <unordered_map>
8#include <unordered_set>
28constexpr auto DatasetField = AQNWB::Types::StorageObjectType::Dataset;
70 return std::filesystem::path(
m_path).filename().string();
77 inline std::shared_ptr<AQNWB::IO::BaseIO>
getIO()
const
79 auto ioPtr =
m_io.lock();
141 "The cache is owned by the I/O so there should be no need to access it "
142 "via RegisteredType. Use getIO()->getRecordingDataCache() instead.")]]
143 inline const std::unordered_map<std::string,
144 std::shared_ptr<IO::BaseRecordingData>>&
147 if (
auto io =
getIO()) {
148 return io->getRecordingDataCache();
150 throw std::runtime_error(
151 "RegisteredType::getCacheRecordingData: IO object is not available");
162 "The cache is owned by the I/O so there should be no need to access it "
163 "via RegisteredType. Use getIO()->clearRecordingDataCache() instead.")]]
166 if (
auto io =
getIO()) {
167 io->clearRecordingDataCache();
182 static std::unordered_set<std::string>&
getRegistry();
195 static std::unordered_map<
197 std::pair<std::function<std::shared_ptr<RegisteredType>(
198 const std::string&, std::shared_ptr<AQNWB::IO::BaseIO>)>,
199 std::pair<std::string, std::string>>>&
221 static std::shared_ptr<RegisteredType>
create(
222 const std::string& fullClassName,
223 const std::string& path,
224 std::shared_ptr<IO::BaseIO> io,
225 bool fallbackToBase =
false);
248 static std::shared_ptr<AQNWB::NWB::RegisteredType>
create(
249 const std::string& path,
250 std::shared_ptr<IO::BaseIO> io,
251 bool fallbackToBase =
false);
269 static inline std::shared_ptr<T>
create(
const std::string& path,
270 std::shared_ptr<AQNWB::IO::BaseIO> io)
272 static_assert(std::is_base_of<RegisteredType, T>::value,
273 "T must be a derived class of RegisteredType");
276 auto casted = std::dynamic_pointer_cast<T>(existing);
280 std::cerr <<
"RegisteredType::create: cached object at path " << path
281 <<
" has type " << existing->getFullTypeName()
282 <<
", which does not match the requested type." << std::endl;
285 auto result = std::shared_ptr<T>(
new T(path, io));
286 result->registerRecordingObject();
350 typename std::enable_if<Types::IsDataStorageObjectType<SOT>::value,
352 inline std::unique_ptr<AQNWB::IO::ReadDataWrapper<SOT, VTYPE>>
readField(
353 const std::string& fieldPath)
const
355 auto ioPtr =
getIO();
357 std::cerr <<
"IO object has been deleted. Can't read field: " << fieldPath
361 return std::make_unique<AQNWB::IO::ReadDataWrapper<SOT, VTYPE>>(
373 inline std::shared_ptr<AQNWB::NWB::RegisteredType>
readField(
374 const std::string& fieldPath)
const
376 auto ioPtr =
getIO();
378 std::cerr <<
"IO object has been deleted. Can't read field: " << fieldPath
403 virtual std::unordered_map<std::string, std::string>
findOwnedTypes(
404 const std::unordered_set<std::string>& types = {},
429 const std::string& path, std::shared_ptr<AQNWB::IO::BaseIO> io);
441 std::shared_ptr<AQNWB::IO::BaseIO> io);
461 const std::string& fullClassName,
462 std::function<std::shared_ptr<RegisteredType>(
463 const std::string&, std::shared_ptr<AQNWB::IO::BaseIO>)>
465 const std::string& typeName,
466 const std::string& typeNamespace);
483 std::weak_ptr<IO::BaseIO>
m_io;
504#define REGISTER_SUBCLASS_WITH_TYPENAME(T, BASE, NAMESPACE_VAR, TYPENAME) \
505 friend class AQNWB::NWB::RegisteredType; \
509 static bool registerSubclass() \
511 AQNWB::NWB::RegisteredType::registerSubclass( \
512 std::string(NAMESPACE_VAR) + "::" + #T, \
513 [](const std::string& path, std::shared_ptr<AQNWB::IO::BaseIO> io) \
514 -> std::shared_ptr<AQNWB::NWB::RegisteredType> \
515 { return RegisteredType::create<T>(path, io); }, \
520 static bool registered_; \
521 virtual std::string getTypeName() const override \
525 virtual std::string getNamespace() const override \
527 return NAMESPACE_VAR; \
529 static std::shared_ptr<T> create(const std::string& path, \
530 std::shared_ptr<AQNWB::IO::BaseIO> io) \
532 return RegisteredType::create<T>(path, io); \
547#define REGISTER_SUBCLASS(T, BASE, NAMESPACE) \
548 REGISTER_SUBCLASS_WITH_TYPENAME(T, BASE, NAMESPACE, #T)
559#define REGISTER_SUBCLASS_IMPL(T) bool T::registered_ = T::registerSubclass();
580#define DEFINE_ATTRIBUTE_FIELD(name, default_type, fieldPath, description) \
589 template<typename VTYPE = default_type> \
590 inline std::unique_ptr< \
591 AQNWB::IO::ReadDataWrapper<AQNWB::NWB::AttributeField, VTYPE>> \
594 auto ioPtr = getIO(); \
596 std::cerr << "IO object has been deleted. Can't read field: " \
597 << fieldPath << std::endl; \
600 return std::make_unique< \
601 AQNWB::IO::ReadDataWrapper<AQNWB::NWB::AttributeField, VTYPE>>( \
602 ioPtr, AQNWB::mergePaths(m_path, fieldPath)); \
626#define DEFINE_DATASET_FIELD( \
627 readName, writeName, default_type, fieldPath, description) \
636 template<typename VTYPE = default_type> \
637 inline std::unique_ptr< \
638 AQNWB::IO::ReadDataWrapper<AQNWB::NWB::DatasetField, VTYPE>> \
641 auto ioPtr = getIO(); \
643 std::cerr << "IO object has been deleted. Can't read field: " \
644 << fieldPath << std::endl; \
647 return std::make_unique< \
648 AQNWB::IO::ReadDataWrapper<AQNWB::NWB::DatasetField, VTYPE>>( \
649 ioPtr, AQNWB::mergePaths(m_path, fieldPath)); \
664 inline std::shared_ptr<AQNWB::IO::BaseRecordingData> writeName(bool reset = \
667 std::string fullPath = AQNWB::mergePaths(m_path, fieldPath); \
668 auto ioPtr = getIO(); \
670 std::cerr << "IO object has been deleted. Can't access: " << fullPath \
674 return ioPtr->getDataSet(fullPath, reset); \
698#define DEFINE_REGISTERED_FIELD(name, registeredType, fieldPath, description) \
711 template<typename RTYPE = registeredType> \
712 inline std::shared_ptr<RTYPE> name() const \
714 std::string objectPath = AQNWB::mergePaths(m_path, fieldPath); \
715 auto ioPtr = getIO(); \
716 if (ioPtr != nullptr) { \
717 if (ioPtr->objectExists(objectPath)) { \
718 return RTYPE::create(objectPath, ioPtr); \
748#define DEFINE_UNNAMED_REGISTERED_FIELD( \
749 readName, writeName, registeredType, fieldPrefixPath, description) \
763 template<typename RTYPE = registeredType> \
764 inline std::shared_ptr<RTYPE> readName(const std::string& objectName) const \
766 std::string prefixPath = AQNWB::mergePaths(m_path, fieldPrefixPath); \
767 std::string objectPath = AQNWB::mergePaths(prefixPath, objectName); \
768 auto ioPtr = getIO(); \
770 std::cerr << "IO object has been deleted. Can't read field: " \
771 << objectPath << std::endl; \
774 if (ioPtr->objectExists(objectPath)) { \
775 return RTYPE::create(objectPath, ioPtr); \
793 template<typename RTYPE = registeredType> \
794 inline std::shared_ptr<RTYPE> writeName(const std::string& objectName) const \
796 std::string prefixPath = AQNWB::mergePaths(m_path, fieldPrefixPath); \
797 std::string objectPath = AQNWB::mergePaths(prefixPath, objectName); \
798 auto ioPtr = getIO(); \
800 std::cerr << "IO object has been deleted. Can't create field: " \
801 << objectPath << std::endl; \
804 return RTYPE::create(objectPath, ioPtr); \
828#define DEFINE_REFERENCED_REGISTERED_FIELD( \
829 name, registeredType, fieldPath, description) \
842 template<typename RTYPE = registeredType> \
843 inline std::shared_ptr<RTYPE> name() const \
846 std::string attrPath = AQNWB::mergePaths(m_path, fieldPath); \
847 auto ioPtr = getIO(); \
848 if (ioPtr != nullptr) { \
849 std::string objectPath = ioPtr->readReferenceAttribute(attrPath); \
850 if (ioPtr->objectExists(objectPath)) { \
851 return RTYPE::create(objectPath, ioPtr); \
854 } catch (const std::exception& e) { \
855 std::cerr << "WARNING Error occurred in " << #name << " " << e.what() \
AQNWB::Types::StorageObjectType StorageObjectType
Definition BaseIO.hpp:20
AQNWB::Types::SizeType SizeType
Definition Channel.hpp:8
std::shared_ptr< AQNWB::NWB::RegisteredType > readField(const std::string &fieldPath) const
Read a field that is itself a RegisteredType.
Definition RegisteredType.hpp:373
const std::string & getPath() const
Gets the path of the registered type.
Definition RegisteredType.hpp:59
std::string getFullTypeName() const
Get the full name of the type, i.e., namespace::typename.
Definition RegisteredType.hpp:323
virtual std::string getTypeName() const
Get the name of the class type.
Definition RegisteredType.cpp:63
static std::shared_ptr< T > create(const std::string &path, std::shared_ptr< AQNWB::IO::BaseIO > io)
Create or retrieve a canonical instance of a RegisteredType subtype.
Definition RegisteredType.hpp:269
std::string m_path
The path of the registered type.
Definition RegisteredType.hpp:471
static const std::string m_defaultUnregisteredDatasetTypeClass
Save the default RegisteredType to use for reading Dataset types that are not registered.
Definition RegisteredType.hpp:449
virtual std::string getNamespace() const
Get the schema namespace of the class type.
Definition RegisteredType.cpp:70
static std::shared_ptr< RegisteredType > create(const std::string &fullClassName, const std::string &path, std::shared_ptr< IO::BaseIO > io, bool fallbackToBase=false)
Create or retrieve the canonical instance of a registered subclass.
Definition RegisteredType.cpp:87
std::weak_ptr< IO::BaseIO > m_io
A weak pointer to the IO object.
Definition RegisteredType.hpp:483
virtual std::unordered_map< std::string, std::string > findOwnedTypes(const std::unordered_set< std::string > &types={}, const AQNWB::IO::SearchMode &search_mode=AQNWB::IO::SearchMode::STOP_ON_TYPE) const
Find all typed objects that are owned by this object, i.e., objects that have a neurodata_type and na...
Definition RegisteredType.cpp:186
SizeType registerRecordingObject()
Register this RegisteredType object with the RecordingObjects manager object of the I/O.
Definition RegisteredType.cpp:161
std::string getName() const
Get the name of the object.
Definition RegisteredType.hpp:68
RegisteredType(const std::string &path, std::shared_ptr< AQNWB::IO::BaseIO > io)
Constructor.
Definition RegisteredType.cpp:18
virtual AQNWB::Types::Status finalize()
Finalize the RegisteredType object.
Definition RegisteredType.cpp:181
static void registerSubclass(const std::string &fullClassName, std::function< std::shared_ptr< RegisteredType >(const std::string &, std::shared_ptr< AQNWB::IO::BaseIO >)> factoryFunction, const std::string &typeName, const std::string &typeNamespace)
Register a subclass name and its factory function in the registry.
Definition RegisteredType.cpp:49
std::shared_ptr< AQNWB::IO::BaseIO > getIO() const
Get a shared pointer to the IO object.
Definition RegisteredType.hpp:77
virtual void clearRecordingDataCache()
Clear the BaseRecordingData object cache to reset the recording state.
Definition RegisteredType.hpp:164
static std::shared_ptr< RegisteredType > getExistingRecordingObject(const std::string &path, std::shared_ptr< AQNWB::IO::BaseIO > io)
Helper to get an existing recording object from the IO object.
Definition RegisteredType.cpp:75
static std::unordered_set< std::string > & getRegistry()
Get the registry of subclass names.
Definition RegisteredType.cpp:27
virtual ~RegisteredType()
Destructor.
Definition RegisteredType.cpp:25
SizeType getRecordingObjectIndex() const
Get the index of this object in m_io->m_recording_objects.
Definition RegisteredType.cpp:212
static const std::string m_defaultUnregisteredGroupTypeClass
Save the default RegisteredType to use for reading Group types that are not registered.
Definition RegisteredType.hpp:445
static std::unordered_map< std::string, std::pair< std::function< std::shared_ptr< RegisteredType >(const std::string &, std::shared_ptr< AQNWB::IO::BaseIO >)>, std::pair< std::string, std::string > > > & getFactoryMap()
Get the factory map for creating instances of subclasses.
Definition RegisteredType.cpp:38
const std::unordered_map< std::string, std::shared_ptr< IO::BaseRecordingData > > & getCacheRecordingData() const
Get the cache of BaseRecordingData objects.
Definition RegisteredType.hpp:145
virtual std::string findOwnedObject(const std::string &name) const
Find the first object owned by this object whose path ends with the given name.
Definition RegisteredType.cpp:200
std::unique_ptr< AQNWB::IO::ReadDataWrapper< SOT, VTYPE > > readField(const std::string &fieldPath) const
Support reading of arbitrary fields by their relative path.
Definition RegisteredType.hpp:352
bool isRegisteredRecordingObject() const
Check if this RegisteredType object is registered in the RecordingObjects manager object of the I/O.
Definition RegisteredType.hpp:95
SearchMode
Enum class for specifying the search mode for findTypes.
Definition BaseIO.hpp:229
@ STOP_ON_TYPE
Stop searching inside an object once a matching type is found.
Definition BaseIO.hpp:233
Namespace for all classes related to the NWB data standard.
constexpr auto AttributeField
Alias for AQNWB::Types::StorageObjectType::Attribute.
Definition RegisteredType.hpp:23
constexpr auto DatasetField
Alias for AQNWB::Types::StorageObjectType::Dataset.
Definition RegisteredType.hpp:28
Status
Represents the status of an operation.
Definition Types.hpp:29
The main namespace for AqNWB.
Definition Channel.hpp:11
static std::string mergePaths(const std::string &path1, const std::string &path2)
Merge two paths into a single path, handling extra trailing and starting "/".
Definition Utils.hpp:264
static bool isValidIndex(SizeType index)
Check if a SizeType index is valid (i.e., not equal to SizeTypeNotSet).
Definition Utils.hpp:362