diff --git a/source/RobotAPI/gui-plugins/ArMemMemoryViewer/ArMemMemoryViewerWidget.ui b/source/RobotAPI/gui-plugins/ArMemMemoryViewer/ArMemMemoryViewerWidget.ui index a972b97b164a83ef25695aaf618e790f250ac09a..3e94dc5e5c3e13bd866c92c428f5d619317806ac 100644 --- a/source/RobotAPI/gui-plugins/ArMemMemoryViewer/ArMemMemoryViewerWidget.ui +++ b/source/RobotAPI/gui-plugins/ArMemMemoryViewer/ArMemMemoryViewerWidget.ui @@ -14,6 +14,26 @@ <string>ArMemMemoryViewerWidget</string> </property> <layout class="QVBoxLayout" name="verticalLayout"> + <item> + <layout class="QHBoxLayout" name="ltmControlWidgetLayout"> + <property name="spacing"> + <number>6</number> + </property> + <item> + <spacer name="horizontalSpacer_2"> + <property name="orientation"> + <enum>Qt::Horizontal</enum> + </property> + <property name="sizeHint" stdset="0"> + <size> + <width>40</width> + <height>20</height> + </size> + </property> + </spacer> + </item> + </layout> + </item> <item> <layout class="QHBoxLayout" name="updateWidgetLayout"> <item> diff --git a/source/RobotAPI/gui-plugins/ArMemMemoryViewer/ArMemMemoryViewerWidgetController.cpp b/source/RobotAPI/gui-plugins/ArMemMemoryViewer/ArMemMemoryViewerWidgetController.cpp index efe81d7170e97515f8bf39e692a16bcd68f1a6fe..f313b6951c2f201251787ec6a6e6b4b5b0026e4c 100644 --- a/source/RobotAPI/gui-plugins/ArMemMemoryViewer/ArMemMemoryViewerWidgetController.cpp +++ b/source/RobotAPI/gui-plugins/ArMemMemoryViewer/ArMemMemoryViewerWidgetController.cpp @@ -41,6 +41,8 @@ namespace armarx widget.setupUi(getWidget()); viewer = std::make_unique<MemoryViewer>( + widget.ltmControlWidgetLayout, + widget.updateWidgetLayout, widget.memoryGroupBox, diff --git a/source/RobotAPI/interface/CMakeLists.txt b/source/RobotAPI/interface/CMakeLists.txt index 547fb0833f1e0475b48a60e8be33979a9dfd09ee..b75d687929475804f31d4f4831b7dc0b7ec82e1c 100644 --- a/source/RobotAPI/interface/CMakeLists.txt +++ b/source/RobotAPI/interface/CMakeLists.txt @@ -113,7 +113,8 @@ set(SLICE_FILES armem/client/MemoryListenerInterface.ice armem/server.ice - armem/server/LongTermMemoryInterface.ice + armem/server/StoringMemoryInterface.ice + armem/server/LoadingMemoryInterface.ice armem/server/MemoryInterface.ice armem/server/MemoryPredictorInterface.ice armem/server/ReadingMemoryInterface.ice diff --git a/source/RobotAPI/interface/armem/io.ice b/source/RobotAPI/interface/armem/io.ice index cccea43c0b749441c30bc1834f3c86ce690b7195..faa262f0bd49228284377f6cefde91f4a9813baa 100644 --- a/source/RobotAPI/interface/armem/io.ice +++ b/source/RobotAPI/interface/armem/io.ice @@ -1,6 +1,6 @@ #pragma once -#include <ArmarXCore/interface/core/PackagePath.ice> +//#include <ArmarXCore/interface/core/PackagePath.ice> #include <RobotAPI/interface/armem/memory.ice> module armarx @@ -11,7 +11,7 @@ module armarx { struct LoadInput { - armarx::data::PackagePath path; + string path; armem::data::MemoryID entityID; }; @@ -31,7 +31,7 @@ module armarx struct StoreInput { - armarx::data::PackagePath path; + string path; armem::data::MemoryID entityID; }; diff --git a/source/RobotAPI/interface/armem/server/LoadingMemoryInterface.ice b/source/RobotAPI/interface/armem/server/LoadingMemoryInterface.ice new file mode 100644 index 0000000000000000000000000000000000000000..0fb10c441f8c34cc9a67823c159f83b8793d946e --- /dev/null +++ b/source/RobotAPI/interface/armem/server/LoadingMemoryInterface.ice @@ -0,0 +1,18 @@ +#pragma once + +#include <RobotAPI/interface/armem/io.ice> + + +module armarx +{ + module armem + { + module server + { + interface LoadingMemoryInterface + { + data::LoadResult load(data::LoadInput input); + }; + }; + }; +}; diff --git a/source/RobotAPI/interface/armem/server/MemoryInterface.ice b/source/RobotAPI/interface/armem/server/MemoryInterface.ice index 93213eed1d85269c83cfcd2547908e2be61f2d2a..03c10c4d3bf52fde5f30c1a5366235a294418195 100644 --- a/source/RobotAPI/interface/armem/server/MemoryInterface.ice +++ b/source/RobotAPI/interface/armem/server/MemoryInterface.ice @@ -1,9 +1,11 @@ #pragma once +#include <RobotAPI/interface/armem/server/LoadingMemoryInterface.ice> +#include <RobotAPI/interface/armem/server/StoringMemoryInterface.ice> + #include <RobotAPI/interface/armem/server/ReadingMemoryInterface.ice> #include <RobotAPI/interface/armem/server/WritingMemoryInterface.ice> -#include <RobotAPI/interface/armem/server/LongTermMemoryInterface.ice> module armarx { @@ -11,7 +13,15 @@ module armarx { module server { - interface MemoryInterface extends ReadingMemoryInterface, WritingMemoryInterface + interface LongTermMemoryInterface extends LoadingMemoryInterface, StoringMemoryInterface + { + }; + + interface ShortTermMemoryInterface extends ReadingMemoryInterface, WritingMemoryInterface + { + }; + + interface MemoryInterface extends ShortTermMemoryInterface, LongTermMemoryInterface { }; }; diff --git a/source/RobotAPI/interface/armem/server/LongTermMemoryInterface.ice b/source/RobotAPI/interface/armem/server/StoringMemoryInterface.ice similarity index 70% rename from source/RobotAPI/interface/armem/server/LongTermMemoryInterface.ice rename to source/RobotAPI/interface/armem/server/StoringMemoryInterface.ice index ba64d626c1c156c3820a508625d1c3a3b36ec847..4e369bf259f24eccb36bcd1a2a58373da0fec442 100644 --- a/source/RobotAPI/interface/armem/server/LongTermMemoryInterface.ice +++ b/source/RobotAPI/interface/armem/server/StoringMemoryInterface.ice @@ -9,9 +9,8 @@ module armarx { module server { - interface LongTermMemoryInterface + interface StoringMemoryInterface { - data::LoadResult load(data::LoadInput input); data::StoreResult store(data::StoreInput input); }; }; diff --git a/source/RobotAPI/libraries/armem/CMakeLists.txt b/source/RobotAPI/libraries/armem/CMakeLists.txt index 844097e2b278b7b4dc2b92bb38daa2ea47aa8123..857a002457871d30a86a3954e35df45a5bca2f75 100644 --- a/source/RobotAPI/libraries/armem/CMakeLists.txt +++ b/source/RobotAPI/libraries/armem/CMakeLists.txt @@ -34,13 +34,16 @@ set(LIB_FILES core/error/ArMemError.cpp - core/io/DiskReaderWriter.cpp - core/io/FileSystemLookupMemory.cpp - core/io/MemoryFileSystemStorage.cpp - core/io/DiskWriter/DiskWriter.cpp - core/io/DiskWriter/NlohmannJSONDiskWriter/NlohmannJSONDiskWriter.cpp - core/io/DiskReader/DiskReader.cpp - core/io/DiskReader/NlohmannJSONDiskReader/NlohmannJSONDiskReader.cpp + core/io/DiskMemory.cpp + core/io/DiskCoreSegment.cpp + core/io/DiskProviderSegment.cpp + core/io/DiskEntity.cpp + core/io/DiskEntitySnapshot.cpp + core/io/DiskEntityInstance.cpp + core/io/diskWriter/DiskWriter.cpp + core/io/diskWriter/NlohmannJSON/NlohmannJSONDiskWriter.cpp + core/io/diskReader/DiskReader.cpp + core/io/diskReader/NlohmannJSON/NlohmannJSONDiskReader.cpp client/ComponentPlugin.cpp client/Reader.cpp @@ -95,13 +98,21 @@ set(LIB_HEADERS core/detail/MemoryItem.h core/detail/TypedEntityContainer.h - core/io/FileSystemLookupMemory.h - core/io/MemoryFileSystemStorage.h - core/io/DiskReaderWriter.h - core/io/DiskWriter/DiskWriter.h - core/io/DiskWriter/NlohmannJSONDiskWriter/NlohmannJSONDiskWriter.h - core/io/DiskReader/DiskReader.h - core/io/DiskReader/NlohmannJSONDiskReader/NlohmannJSONDiskReader.h + core/io/DiskInstanceData.h + core/io/DiskMemory.h + core/io/DiskCoreSegment.h + core/io/DiskProviderSegment.h + core/io/DiskEntity.h + core/io/DiskEntitySnapshot.h + core/io/DiskEntityInstance.h + core/io/diskWriter/DiskWriter.h + core/io/diskWriter/NlohmannJSON/NlohmannJSONDiskWriter.h + core/io/diskReader/DiskReader.h + core/io/diskReader/NlohmannJSON/NlohmannJSONDiskReader.h + + core/io/detail/DiskMemoryItem.h + core/io/detail/DiskMemoryContainer.h + core/io/detail/DiskTypedEntityContainer.h client.h client/ComponentPlugin.h diff --git a/source/RobotAPI/libraries/armem/client/Reader.h b/source/RobotAPI/libraries/armem/client/Reader.h index 76795ad5edf87bbd14f893f82811292915718382..620744c57c000e4f91d940dcb8f938833bb4a1af 100644 --- a/source/RobotAPI/libraries/armem/client/Reader.h +++ b/source/RobotAPI/libraries/armem/client/Reader.h @@ -11,6 +11,7 @@ #include <RobotAPI/interface/armem/client/MemoryListenerInterface.h> #include <RobotAPI/libraries/armem/core/ice_conversions.h> #include <RobotAPI/libraries/armem/core/Memory.h> +#include <RobotAPI/libraries/armem/core/io/DiskMemory.h> #include "Query.h" diff --git a/source/RobotAPI/libraries/armem/core/CoreSegment.cpp b/source/RobotAPI/libraries/armem/core/CoreSegment.cpp index 61098ee9a268d6bd06748c02878cc70e013e72af..92857a7bc72e447cda83e279db369287c0fca13e 100644 --- a/source/RobotAPI/libraries/armem/core/CoreSegment.cpp +++ b/source/RobotAPI/libraries/armem/core/CoreSegment.cpp @@ -41,6 +41,7 @@ namespace armarx::armem bool CoreSegment::equalsDeep(const CoreSegment& other) const { + //std::cout << "CoreSegment::equalsDeep" << std::endl; if (size() != other.size()) { return false; diff --git a/source/RobotAPI/libraries/armem/core/Entity.cpp b/source/RobotAPI/libraries/armem/core/Entity.cpp index 876f5a19b63f6667c6e591644eef0ed2c5b71e09..9795ffdbe0f51cb4ef9fbb562fd10929020a95c1 100644 --- a/source/RobotAPI/libraries/armem/core/Entity.cpp +++ b/source/RobotAPI/libraries/armem/core/Entity.cpp @@ -37,6 +37,7 @@ namespace armarx::armem bool Entity::equalsDeep(const Entity& other) const { + //std::cout << "Entity::equalsDeep" << std::endl; if (size() != other.size()) { return false; diff --git a/source/RobotAPI/libraries/armem/core/EntityInstance.cpp b/source/RobotAPI/libraries/armem/core/EntityInstance.cpp index 416e56d740acb7701557e8ade3b98a4d1eb410b4..c498216cfb0089551263a42478295f0da3b3d7d5 100644 --- a/source/RobotAPI/libraries/armem/core/EntityInstance.cpp +++ b/source/RobotAPI/libraries/armem/core/EntityInstance.cpp @@ -22,6 +22,7 @@ namespace armarx::armem bool EntityInstance::equalsDeep(const EntityInstance& other) const { + //std::cout << "EntityInstance::equalsDeep" << std::endl; return _metadata == other.metadata() && _data->equalsDeep(other.data()); } diff --git a/source/RobotAPI/libraries/armem/core/EntitySnapshot.cpp b/source/RobotAPI/libraries/armem/core/EntitySnapshot.cpp index 7a53400f9c75849c805e443e61afafc83f43e7c0..9d9eac2a65b4bb6e55c25b4d4252fbd9e97f26b1 100644 --- a/source/RobotAPI/libraries/armem/core/EntitySnapshot.cpp +++ b/source/RobotAPI/libraries/armem/core/EntitySnapshot.cpp @@ -36,6 +36,7 @@ namespace armarx::armem bool EntitySnapshot::equalsDeep(const EntitySnapshot& other) const { + //std::cout << "EntitySnapshot::equalsDeep" << std::endl; if (size() != other.size()) { return false; diff --git a/source/RobotAPI/libraries/armem/core/Memory.cpp b/source/RobotAPI/libraries/armem/core/Memory.cpp index 3d218f0b098670cbc6e704e9e500ffecd752c2ac..748e47495b998bfe6149f4aa94483f2ea23d02e4 100644 --- a/source/RobotAPI/libraries/armem/core/Memory.cpp +++ b/source/RobotAPI/libraries/armem/core/Memory.cpp @@ -152,6 +152,7 @@ namespace armarx::armem bool Memory::equalsDeep(const Memory& other) const { + //std::cout << "Memory::equalsDeep" << std::endl; if (size() != other.size()) { return false; diff --git a/source/RobotAPI/libraries/armem/core/ProviderSegment.cpp b/source/RobotAPI/libraries/armem/core/ProviderSegment.cpp index 879932739ff86a8a9b091d561053f0f76ca08be0..1eabd5ecf36b60fdcd0af52e4b3d43770b914fe9 100644 --- a/source/RobotAPI/libraries/armem/core/ProviderSegment.cpp +++ b/source/RobotAPI/libraries/armem/core/ProviderSegment.cpp @@ -41,6 +41,7 @@ namespace armarx::armem bool ProviderSegment::equalsDeep(const ProviderSegment& other) const { + //std::cout << "ProviderSegment::equalsDeep" << std::endl; if (size() != other.size()) { return false; diff --git a/source/RobotAPI/libraries/armem/core/io/DiskCoreSegment.cpp b/source/RobotAPI/libraries/armem/core/io/DiskCoreSegment.cpp new file mode 100644 index 0000000000000000000000000000000000000000..caae29404b0a9c7b93d11a4958d81eea72d85a88 --- /dev/null +++ b/source/RobotAPI/libraries/armem/core/io/DiskCoreSegment.cpp @@ -0,0 +1,179 @@ +#include "DiskCoreSegment.h" + +namespace armarx::armem::io +{ + // copy + DiskCoreSegment::DiskCoreSegment(const DiskCoreSegment& x): + DiskTypedEntityContainer(x.storagePath, x.reader), + diskProviderSegments(x.diskProviderSegments) + { + //std::cout << "Copy DiskCoreSegment" << std::endl; + } + + // load + DiskCoreSegment::DiskCoreSegment(const std::filesystem::path& loadFrom, const DiskReaderPtr& r) : + DiskTypedEntityContainer(loadFrom, r) + { + //std::cout << "Create DiskCoreSegment" << std::endl; + append(loadFrom, r); + } + + // store + DiskCoreSegment::DiskCoreSegment(const CoreSegment& c, const std::filesystem::path& storeAt, const DiskWriterPtr& w) : + DiskTypedEntityContainer(storeAt, w->getCorrespondingDiskReader()) + { + //std::cout << "Create DiskCoreSegment" << std::endl; + append(c, storeAt, w); + } + + // operators + std::string DiskCoreSegment::toString() const + { + std::string endl = "\n"; + std::string tab = " "; + + std::stringstream ss; + ss << "{" << std::endl; + for (const auto& [key, p] : diskProviderSegments) + { + ss << tab << key << ":" << endl; + for (const auto& l : simox::alg::split(p.toString(), endl, false)) + { + ss << tab << l << endl; + } + } + ss << "}" << endl; + return ss.str(); + } + + DiskCoreSegment& DiskCoreSegment::operator=(const DiskCoreSegment& x) + { + storagePath = x.storagePath; + reader = x.reader; + diskProviderSegments = x.diskProviderSegments; + return *this; + } + + bool DiskCoreSegment::hasProviderSegment(const std::string& key) const + { + return diskProviderSegments.find(key) != diskProviderSegments.end(); + } + + DiskProviderSegment DiskCoreSegment::getProviderSegment(const std::string& key) const + { + if (!hasProviderSegment(key)) + { + throw error::InvalidArgument("key", "DiskCoreSegment::getProviderSegment", "The providersegment does not exist."); + } + return diskProviderSegments.at(key); + } + + const std::map<std::string, DiskProviderSegment>& DiskCoreSegment::getProviderSegments() const + { + return diskProviderSegments; + } + + + void DiskCoreSegment::append(const CoreSegment& c, const std::filesystem::path& storeAt, const DiskWriterPtr& w) + { + if (!std::filesystem::is_directory(storeAt)) + { + throw error::PathNotADirectory(storeAt, "Can not store a coresegment at this place."); + } + + initializeIf(storeAt, w->getCorrespondingDiskReader()); + + for (const auto& [key, p] : c.providerSegments) + { + std::filesystem::path pStoreAt = storeAt / key; + if (!std::filesystem::is_directory(pStoreAt)) + { + std::filesystem::create_directory(pStoreAt); + } + + if (c.aronType() != nullptr) + { + std::filesystem::path typeStoragePath = getStoragePath() / (std::string(TYPE_FILENAME) + "." + w->getTypeFileSuffix()); + w->writeTypeInstance(c.aronType(), typeStoragePath); + } + + DiskProviderSegment d(p, pStoreAt, w); + insert(key, d); + } + } + + void DiskCoreSegment::append(const std::filesystem::path& loadFrom, const DiskReaderPtr& r) + { + if (loadFrom != storagePath) + { + throw error::ArMemError("Can not append a different path to a coresegment."); + } + + if (!std::filesystem::is_directory(loadFrom)) + { + throw error::PathNotADirectory(loadFrom, "Can not load a coresegment from this place."); + } + + initializeIf(loadFrom, r); + + for (const auto& p : std::filesystem::directory_iterator(loadFrom)) + { + if (!std::filesystem::is_directory(p)) + { + continue; + } + + std::string key = p.path().filename(); + DiskProviderSegment x(p, r); + insert(key, x); + } + } + + void DiskCoreSegment::append(const DiskCoreSegment& d) + { + if (d.storagePath != storagePath) + { + throw error::ArMemError("Can not append a diskmemory with different path to a coresegment."); + } + + initializeIf(d.storagePath, d.reader); + + for (const auto& [key, p] : d.diskProviderSegments) + { + insert(key, p); + } + } + + void DiskCoreSegment::insert(const std::string& key, const DiskProviderSegment& p) + { + if (hasProviderSegment(key)) + { + diskProviderSegments.at(key).append(p); + } + else + { + diskProviderSegments.insert(std::make_pair(key, p)); + } + } + + CoreSegment DiskCoreSegment::toCoreSegment(const aoType& mType) const + { + // converts the stored references to a real CoreSegment + //std::cout << "toCoreSegment" << std::endl; + CoreSegment s; + for (const auto& [key, p] : diskProviderSegments) + { + auto x = p.toProviderSegment(mType, getStoredObjectType()); + x.name() = key; + s.addProviderSegment(x); + } + return s; + } + + aron::typenavigator::ObjectNavigatorPtr DiskCoreSegment::getStoredObjectType() const + { + //std::cout << "DiskCoreSegment: readStoredObjectType" << std::endl; + std::filesystem::path t = storagePath / (std::string(TYPE_FILENAME) + "." + reader->getTypeFileSuffix()); + return reader->readTypeInstance(t); + } +} diff --git a/source/RobotAPI/libraries/armem/core/io/DiskCoreSegment.h b/source/RobotAPI/libraries/armem/core/io/DiskCoreSegment.h new file mode 100644 index 0000000000000000000000000000000000000000..5c8963183d9472ae9f93bf3bacad25877f61bae4 --- /dev/null +++ b/source/RobotAPI/libraries/armem/core/io/DiskCoreSegment.h @@ -0,0 +1,79 @@ +/* +* This file is part of ArmarX. +* +* ArmarX is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* ArmarX is distributed in the hope that it will be useful, but +* WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* @author Fabian Peller (fabian dot peller at kit dot edu) +* @copyright http://www.gnu.org/licenses/gpl-2.0.txt +* GNU General Public License +*/ + +#pragma once + +// STD/STL +#include <map> +#include <string> +#include <vector> + +// BaseClass +#include "detail/DiskTypedEntityContainer.h" + +// ArmarX +#include "../CoreSegment.h" +#include "DiskProviderSegment.h" + + +namespace armarx::armem::io +{ + class DiskCoreSegment : + virtual public DiskTypedEntityContainer + { + using aoType = aron::typenavigator::ObjectNavigatorPtr; + + public: + DiskCoreSegment() = default; + + // copy + DiskCoreSegment(const DiskCoreSegment&); + + // load + DiskCoreSegment(const std::filesystem::path&, const DiskReaderPtr&); + + // store + DiskCoreSegment(const CoreSegment&, const std::filesystem::path&, const DiskWriterPtr&); + + // operators + std::string toString() const; + DiskCoreSegment& operator=(const DiskCoreSegment&); + + // virtual + virtual aron::typenavigator::ObjectNavigatorPtr getStoredObjectType() const override; + + // public methods + bool hasProviderSegment(const std::string& key) const; + + DiskProviderSegment getProviderSegment(const std::string& key) const; + const std::map<std::string, DiskProviderSegment>& getProviderSegments() const; + + CoreSegment toCoreSegment(const aoType& mType = nullptr) const; + + void append(const CoreSegment&, const std::filesystem::path&, const DiskWriterPtr&); + void append(const std::filesystem::path&, const DiskReaderPtr& r); + void append(const DiskCoreSegment&); + + void insert(const std::string& key, const DiskProviderSegment&); + + private: + std::map<std::string, DiskProviderSegment> diskProviderSegments; + }; +} diff --git a/source/RobotAPI/libraries/armem/core/io/DiskEntity.cpp b/source/RobotAPI/libraries/armem/core/io/DiskEntity.cpp new file mode 100644 index 0000000000000000000000000000000000000000..1d6b799ed7e4d33f242f26ffc5921433277c7584 --- /dev/null +++ b/source/RobotAPI/libraries/armem/core/io/DiskEntity.cpp @@ -0,0 +1,179 @@ +#include "DiskEntity.h" + +namespace armarx::armem::io +{ + // copy + DiskEntity::DiskEntity(const DiskEntity& x): + DiskTypedEntityContainer(x.storagePath, x.reader), + diskEntityHistory(x.diskEntityHistory) + { + } + + // load + DiskEntity::DiskEntity(const std::filesystem::path& loadFrom, const DiskReaderPtr& r) : + DiskTypedEntityContainer(loadFrom, r) + { + //std::cout << "Create DiskEntity" << std::endl; + append(loadFrom, r); + } + + // store + DiskEntity::DiskEntity(const Entity& c, const std::filesystem::path& storeAt, const DiskWriterPtr& w) : + DiskTypedEntityContainer(storeAt, w->getCorrespondingDiskReader()) + { + //std::cout << "Create DiskEntity" << std::endl; + append(c, storeAt, w); + } + + // operators + std::string DiskEntity::toString() const + { + std::string endl = "\n"; + std::string tab = " "; + + std::stringstream ss; + ss << "{" << std::endl; + for (const auto& [key, p] : diskEntityHistory) + { + ss << tab << std::to_string(key.toMicroSeconds()) << ":" << endl; + for (const auto& l : simox::alg::split(p.toString(), endl, false)) + { + ss << tab << l << endl; + } + } + ss << "}" << endl; + return ss.str(); + } + + DiskEntity& DiskEntity::operator=(const DiskEntity& x) + { + storagePath = x.storagePath; + reader = x.reader; + diskEntityHistory = x.diskEntityHistory; + return *this; + } + + bool DiskEntity::hasEntitySnapshot(const armem::Time& key) const + { + return diskEntityHistory.find(key) != diskEntityHistory.end(); + } + + DiskEntitySnapshot DiskEntity::getEntitySnapshot(const armem::Time& key) const + { + if (!hasEntitySnapshot(key)) + { + throw error::InvalidArgument("key", "DiskEntity::getEntitySnapshot", "The Entity does not exist."); + } + return diskEntityHistory.at(key); + } + + const std::map<armem::Time, DiskEntitySnapshot>& DiskEntity::getEntitySnapshots() const + { + return diskEntityHistory; + } + + void DiskEntity::append(const Entity& c, const std::filesystem::path& storeAt, const DiskWriterPtr& w) + { + if (!std::filesystem::is_directory(storeAt)) + { + throw error::PathNotADirectory(storeAt, ""); + } + + initializeIf(storeAt, w->getCorrespondingDiskReader()); + + for (const auto& [key, p] : c.history) + { + std::filesystem::path pStoreAt = storeAt / std::to_string(key.toMicroSeconds()); + if (!std::filesystem::is_directory(pStoreAt)) + { + std::filesystem::create_directory(pStoreAt); + } + + auto d = DiskEntitySnapshot(p, pStoreAt, w); + if (auto it = diskEntityHistory.find(key); it == diskEntityHistory.end()) + { + diskEntityHistory.insert(std::make_pair(key, d)); + } + else + { + it->second.append(d); + } + } + } + + void DiskEntity::append(const std::filesystem::path& loadFrom, const DiskReaderPtr& r) + { + if (loadFrom != storagePath) + { + throw error::ArMemError("Can not append a different path to an entity."); + } + + if (!std::filesystem::is_directory(loadFrom)) + { + throw error::PathNotADirectory(loadFrom, "Can not load an entity from this place."); + } + + initializeIf(loadFrom, r); + + for (const auto& p : std::filesystem::directory_iterator(loadFrom)) + { + if (!std::filesystem::is_directory(p)) + { + continue; + } + + std::string f = p.path().filename(); + armem::Time key = armem::Time::microSeconds(std::stol(f)); + auto x = DiskEntitySnapshot(p, r); + insert(key, x); + } + } + + void DiskEntity::append(const DiskEntity& d) + { + if (d.storagePath != storagePath) + { + throw error::ArMemError("Can not append a diskmemory with different path to an entity."); + } + + initializeIf(d.storagePath, d.reader); + + for (const auto& [key, p] : d.diskEntityHistory) + { + insert(key, p); + } + } + + void DiskEntity::insert(const armem::Time& key, const DiskEntitySnapshot& p) + { + if (hasEntitySnapshot(key)) + { + diskEntityHistory.at(key).append(p); + } + else + { + diskEntityHistory.insert(std::make_pair(key, p)); + } + } + + aron::typenavigator::ObjectNavigatorPtr DiskEntity::getStoredObjectType() const + { + //std::cout << "DiskEntity: readStoredObjectType" << std::endl; + std::filesystem::path t = storagePath / (std::string(TYPE_FILENAME) + "." + reader->getTypeFileSuffix()); + return reader->readTypeInstance(t); + } + + Entity DiskEntity::toEntity(const aoType& mType, const aoType& cType, const aoType& pType) const + { + // converts the stored references to a real Entity + //std::cout << "tpEntity" << std::endl; + Entity s; + for (const auto& [key, p] : diskEntityHistory) + { + auto x = p.toEntitySnapshot(mType, cType, pType, getStoredObjectType()); + x.time() = key; + s.addSnapshot(x); + } + return s; + } +} diff --git a/source/RobotAPI/libraries/armem/core/io/DiskEntity.h b/source/RobotAPI/libraries/armem/core/io/DiskEntity.h new file mode 100644 index 0000000000000000000000000000000000000000..6fae8d06973070e01b6c332439efe5e15f2f4f3d --- /dev/null +++ b/source/RobotAPI/libraries/armem/core/io/DiskEntity.h @@ -0,0 +1,81 @@ +/* +* This file is part of ArmarX. +* +* ArmarX is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* ArmarX is distributed in the hope that it will be useful, but +* WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* @author Fabian Peller (fabian dot peller at kit dot edu) +* @copyright http://www.gnu.org/licenses/gpl-2.0.txt +* GNU General Public License +*/ + +#pragma once + +// STD/STL +#include <map> +#include <string> +#include <vector> + +// BaseClass +#include "detail/DiskTypedEntityContainer.h" + +// ArmarX +#include "../Entity.h" +#include "../../core/Time.h" +#include "DiskEntitySnapshot.h" + + +namespace armarx::armem::io +{ + + class DiskEntity : + virtual public DiskTypedEntityContainer + { + using aoType = aron::typenavigator::ObjectNavigatorPtr; + + public: + DiskEntity() = default; + + // copy + DiskEntity(const DiskEntity&); + + // load + DiskEntity(const std::filesystem::path&, const DiskReaderPtr&); + + // store + DiskEntity(const Entity&, const std::filesystem::path&, const DiskWriterPtr&); + + // operators + std::string toString() const; + DiskEntity& operator=(const DiskEntity&); + + // virtual + virtual aron::typenavigator::ObjectNavigatorPtr getStoredObjectType() const override; + + // public methods + bool hasEntitySnapshot(const armem::Time&) const; + + DiskEntitySnapshot getEntitySnapshot(const armem::Time&) const; + const std::map<armem::Time, DiskEntitySnapshot>& getEntitySnapshots() const; + + Entity toEntity(const aoType& mType = nullptr, const aoType& cType = nullptr, const aoType& pType = nullptr) const; + + void append(const Entity&, const std::filesystem::path&, const DiskWriterPtr&); + void append(const std::filesystem::path&, const DiskReaderPtr&); + void append(const DiskEntity&); + + void insert(const armem::Time& key, const DiskEntitySnapshot&); + + private: + std::map<armem::Time, DiskEntitySnapshot> diskEntityHistory; + }; +} diff --git a/source/RobotAPI/libraries/armem/core/io/DiskEntityInstance.cpp b/source/RobotAPI/libraries/armem/core/io/DiskEntityInstance.cpp new file mode 100644 index 0000000000000000000000000000000000000000..21faf40f8b96ef6e84fead552339427de48d67c9 --- /dev/null +++ b/source/RobotAPI/libraries/armem/core/io/DiskEntityInstance.cpp @@ -0,0 +1,109 @@ +#include "DiskEntityInstance.h" + +#include "DiskEntitySnapshot.h" +#include "DiskEntity.h" +#include "DiskProviderSegment.h" +#include "DiskCoreSegment.h" +#include "DiskMemory.h" + +#include "diskWriter/NlohmannJSON/NlohmannJSONDiskWriter.h" +#include "diskReader/NlohmannJSON/NlohmannJSONDiskReader.h" + +namespace armarx::armem::io +{ + // copy + DiskEntityInstance::DiskEntityInstance(const DiskEntityInstance& x): + DiskTypedEntityContainer(x.storagePath, x.reader), + dataStoragePath(x.dataStoragePath) + { + } + + // load + DiskEntityInstance::DiskEntityInstance(const std::filesystem::path& loadFrom, const DiskReaderPtr& r) : + DiskTypedEntityContainer(loadFrom, r) + { + //std::cout << "Create DiskEntityInstance" << std::endl; + std::filesystem::path pa = loadFrom / (std::string(DATA_FILENAME) + "." + reader->getDataFileSuffix()); + if (!std::filesystem::is_regular_file(pa)) + { + throw error::PathNotARegularFile(pa, "Could not load a stored entity instance"); + } + dataStoragePath = pa; + } + + // store + DiskEntityInstance::DiskEntityInstance(const EntityInstance& c, const std::filesystem::path& storeAt, const DiskWriterPtr& w) : + DiskTypedEntityContainer(storeAt, w->getCorrespondingDiskReader()) + { + //std::cout << "Create DiskEntityInstance" << std::endl; + if (!std::filesystem::is_directory(storeAt)) + { + throw error::PathNotADirectory(storeAt, ""); + } + + dataStoragePath = storeAt / (std::string(DATA_FILENAME) + "." + w->getDataFileSuffix()); + w->writeInstance(c, dataStoragePath); + } + + // operators + std::string DiskEntityInstance::toString() const + { + std::string endl = "\n"; + std::string tab = " "; + + std::stringstream ss; + ss << "{" << std::endl; + ss << tab << "Path: " << dataStoragePath.string() << endl; + ss << "}" << endl; + return ss.str(); + } + + DiskEntityInstance& DiskEntityInstance::operator=(const DiskEntityInstance& x) + { + storagePath = x.storagePath; + reader = x.reader; + dataStoragePath = x.dataStoragePath; + return *this; + } + + aron::typenavigator::ObjectNavigatorPtr DiskEntityInstance::getStoredObjectType() const + { + //std::cout << "DiskEntityInstance: readStoredObjectType" << std::endl; + std::filesystem::path t = storagePath / (std::string(TYPE_FILENAME) + "." + reader->getTypeFileSuffix()); + return reader->readTypeInstance(t); + } + + EntityInstance DiskEntityInstance::toEntityInstance(const aoType& mType, const aoType& cType, const aoType& pType, const aoType& eType, const aoType& sType) const + { + // converts the stored references to a real EntityInstance + //std::cout << "toEntityInstance" << std::endl; + + auto iType = getStoredObjectType(); + if (iType != nullptr) + { + return reader->readInstance(dataStoragePath, iType); + } + + if (sType != nullptr) // entitySnapshot + { + return reader->readInstance(dataStoragePath, sType); + } + + if (eType != nullptr) // entity + { + return reader->readInstance(dataStoragePath, eType); + } + + if (pType != nullptr) // providerSegment + { + return reader->readInstance(dataStoragePath, pType); + } + + if (cType != nullptr) // coreSegment + { + return reader->readInstance(dataStoragePath, cType); + } + + return reader->readInstance(dataStoragePath, mType); + } +} diff --git a/source/RobotAPI/libraries/armem/core/io/DiskEntityInstance.h b/source/RobotAPI/libraries/armem/core/io/DiskEntityInstance.h new file mode 100644 index 0000000000000000000000000000000000000000..c526f49ddb644080822474a76ad9d788d50248f5 --- /dev/null +++ b/source/RobotAPI/libraries/armem/core/io/DiskEntityInstance.h @@ -0,0 +1,71 @@ +/* +* This file is part of ArmarX. +* +* ArmarX is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* ArmarX is distributed in the hope that it will be useful, but +* WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* @author Fabian Peller (fabian dot peller at kit dot edu) +* @copyright http://www.gnu.org/licenses/gpl-2.0.txt +* GNU General Public License +*/ + +#pragma once + +// STD/STL +#include <map> +#include <string> +#include <vector> +#include <filesystem> + +// BaseClass +#include "detail/DiskTypedEntityContainer.h" + +// ArmarX +#include "../EntityInstance.h" +#include "../MemoryID.h" +#include "../error.h" + +namespace armarx::armem::io +{ + class DiskEntityInstance : + virtual public DiskTypedEntityContainer + { + using aoType = aron::typenavigator::ObjectNavigatorPtr; + + public: + DiskEntityInstance() = default; + + // copy + DiskEntityInstance(const DiskEntityInstance&); + + // load + DiskEntityInstance(const std::filesystem::path&, const DiskReaderPtr&); + + // store + DiskEntityInstance(const EntityInstance&, const std::filesystem::path&, const DiskWriterPtr&); + + // operators + std::string toString() const; + DiskEntityInstance& operator=(const DiskEntityInstance&); + + // virtual + virtual aron::typenavigator::ObjectNavigatorPtr getStoredObjectType() const override; + + // public methods + EntityInstance toEntityInstance(const aoType& mType = nullptr, const aoType& cType = nullptr, const aoType& pType = nullptr, const aoType& eType = nullptr, const aoType& sType = nullptr) const; + + private: + std::filesystem::path dataStoragePath; + + static constexpr const char* DATA_FILENAME = "data"; + }; +} diff --git a/source/RobotAPI/libraries/armem/core/io/DiskEntitySnapshot.cpp b/source/RobotAPI/libraries/armem/core/io/DiskEntitySnapshot.cpp new file mode 100644 index 0000000000000000000000000000000000000000..e6d94c6166bbdf4b5428167a92fe4f96eac223c6 --- /dev/null +++ b/source/RobotAPI/libraries/armem/core/io/DiskEntitySnapshot.cpp @@ -0,0 +1,191 @@ +#include "DiskEntitySnapshot.h" + +#include "DiskEntity.h" + +namespace armarx::armem::io +{ + // copy + DiskEntitySnapshot::DiskEntitySnapshot(const DiskEntitySnapshot& x): + DiskTypedEntityContainer(x.storagePath, x.reader), + diskEntityInstances(x.diskEntityInstances) + { + } + + // load + DiskEntitySnapshot::DiskEntitySnapshot(const std::filesystem::path& loadFrom, const DiskReaderPtr& r) : + DiskTypedEntityContainer(loadFrom, r) + { + //std::cout << "Create DiskEntitySnapshot" << std::endl; + append(loadFrom, r); + } + + // store + DiskEntitySnapshot::DiskEntitySnapshot(const EntitySnapshot& c, const std::filesystem::path& storeAt, const DiskWriterPtr& w) : + DiskTypedEntityContainer(storeAt, w->getCorrespondingDiskReader()) + { + //std::cout << "Create DiskEntitySnapshot" << std::endl; + + append(c, storeAt, w); + } + + // operators + std::string DiskEntitySnapshot::toString() const + { + std::string endl = "\n"; + std::string tab = " "; + + std::stringstream ss; + ss << "{" << std::endl; + + unsigned int i = 0; + for (const auto& p : diskEntityInstances) + { + ss << tab << std::to_string(i++) << ":" << endl; + for (const auto& l : simox::alg::split(p.toString(), endl, false)) + { + ss << tab << l << endl; + } + } + ss << "}" << endl; + return ss.str(); + } + + DiskEntitySnapshot& DiskEntitySnapshot::operator=(const DiskEntitySnapshot& x) + { + storagePath = x.storagePath; + reader = x.reader; + diskEntityInstances = x.diskEntityInstances; + return *this; + } + + aron::typenavigator::ObjectNavigatorPtr DiskEntitySnapshot::getStoredObjectType() const + { + //std::cout << "DiskEntitySnapshot: readStoredObjectType" << std::endl; + std::filesystem::path t = storagePath / (std::string(TYPE_FILENAME) + "." + reader->getTypeFileSuffix()); + return reader->readTypeInstance(t); + } + + bool DiskEntitySnapshot::hasEntityInstance(const unsigned int key) const + { + return diskEntityInstances.size() > key; + } + + DiskEntityInstance DiskEntitySnapshot::getEntityInstance(const unsigned int key) const + { + if (!hasEntityInstance(key)) + { + throw error::InvalidArgument("key", "DiskEntitySnapshot::getEntityInstance", "The entitysnapshot does not exist."); + } + return diskEntityInstances.at(key); + } + + const std::vector<DiskEntityInstance>& DiskEntitySnapshot::getEntityInstances() const + { + return diskEntityInstances; + } + + void DiskEntitySnapshot::append(const EntitySnapshot& c, const std::filesystem::path& storeAt, const DiskWriterPtr& w) + { + if (!std::filesystem::is_directory(storeAt)) + { + throw error::PathNotADirectory(storeAt, ""); + } + + initializeIf(storeAt, w->getCorrespondingDiskReader()); + + unsigned int i = 0; + for (const auto& p : c.instances) + { + if (i < diskEntityInstances.size()) + { + // WARNING: The snapshot already has values in its managed container. Appending data at end + // TODO: print warning + continue; + } + + std::filesystem::path pStoreAt = storeAt / std::to_string(i++); + if (!std::filesystem::is_directory(pStoreAt)) + { + std::filesystem::create_directory(pStoreAt); + } + + auto d = DiskEntityInstance(p, pStoreAt, w); + diskEntityInstances.push_back(d); + } + } + + void DiskEntitySnapshot::append(const std::filesystem::path& loadFrom, const DiskReaderPtr& r) + { + if (loadFrom != storagePath) + { + throw error::ArMemError("Can not append a different path to an entitysnapshot."); + } + + if (!std::filesystem::is_directory(loadFrom)) + { + throw error::PathNotADirectory(loadFrom, "Can not load an entity from this place."); + } + + initializeIf(loadFrom, r); + + for (unsigned int i = 0; i < 10000; ++i) + { + std::filesystem::path p = loadFrom / std::to_string(i); + if (!std::filesystem::is_directory(p)) + { + // there is no other instance in snapshot + break; + } + + if (i < diskEntityInstances.size()) + { + // WARNING: We ignore instances that already exist. + continue; + } + + auto x = DiskEntityInstance(p, r); + insert(x); + } + } + + void DiskEntitySnapshot::append(const DiskEntitySnapshot& d) + { + if (d.storagePath != storagePath) + { + throw error::ArMemError("Can not append a diskmemory with different path to an entitysnapshot."); + } + + initializeIf(d.storagePath, d.reader); + + unsigned int i = 0; + for (const auto& p : d.diskEntityInstances) + { + if (i < diskEntityInstances.size()) + { + // WARNING: We ignore instances that already exist. + continue; + } + insert(p); + } + } + + void DiskEntitySnapshot::insert(const DiskEntityInstance& p) + { + diskEntityInstances.push_back(p); + } + + EntitySnapshot DiskEntitySnapshot::toEntitySnapshot(const aoType& mType, const aoType& cType, const aoType& pType, const aoType& eType) const + { + // converts the stored references to a real EntitySnapshot + //std::cout << "toEntitySnapshot" << std::endl; + EntitySnapshot s; + unsigned int i = 0; + for (const auto& p : diskEntityInstances) + { + auto x = p.toEntityInstance(mType, cType, pType, eType, getStoredObjectType()); + x.index() = i; + s.addInstance(x); + } + return s; + } +} diff --git a/source/RobotAPI/libraries/armem/core/io/DiskEntitySnapshot.h b/source/RobotAPI/libraries/armem/core/io/DiskEntitySnapshot.h new file mode 100644 index 0000000000000000000000000000000000000000..fe35e9c8d03f9ba8737eb0fc7c802156b2dbe4ba --- /dev/null +++ b/source/RobotAPI/libraries/armem/core/io/DiskEntitySnapshot.h @@ -0,0 +1,80 @@ +/* +* This file is part of ArmarX. +* +* ArmarX is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* ArmarX is distributed in the hope that it will be useful, but +* WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* @author Fabian Peller (fabian dot peller at kit dot edu) +* @copyright http://www.gnu.org/licenses/gpl-2.0.txt +* GNU General Public License +*/ + +#pragma once + +// STD/STL +#include <map> +#include <string> +#include <vector> + +// BaseClass +#include "detail/DiskTypedEntityContainer.h" + +// ArmarX +#include "../EntitySnapshot.h" +#include "DiskEntityInstance.h" + + +namespace armarx::armem::io +{ + + class DiskEntitySnapshot : + virtual public DiskTypedEntityContainer + { + using aoType = aron::typenavigator::ObjectNavigatorPtr; + + public: + DiskEntitySnapshot() = default; + + // copy + DiskEntitySnapshot(const DiskEntitySnapshot&); + + // load + DiskEntitySnapshot(const std::filesystem::path&, const DiskReaderPtr&); + + // store + DiskEntitySnapshot(const EntitySnapshot&, const std::filesystem::path&, const DiskWriterPtr&); + + // operators + std::string toString() const; + DiskEntitySnapshot& operator=(const DiskEntitySnapshot&); + + // virtual + aron::typenavigator::ObjectNavigatorPtr getStoredObjectType() const override; + + // public methods + bool hasEntityInstance(const unsigned int) const; + + DiskEntityInstance getEntityInstance(const unsigned int) const; + const std::vector<DiskEntityInstance>& getEntityInstances() const; + + EntitySnapshot toEntitySnapshot(const aoType& mType = nullptr, const aoType& cType = nullptr, const aoType& pType = nullptr, const aoType& eType = nullptr) const; + + void append(const EntitySnapshot&, const std::filesystem::path&, const DiskWriterPtr&); + void append(const std::filesystem::path&, const DiskReaderPtr&); + void append(const DiskEntitySnapshot&); + + void insert(const DiskEntityInstance&); + + private: + std::vector<DiskEntityInstance> diskEntityInstances; + }; +} diff --git a/source/RobotAPI/libraries/armem/core/io/DiskInstanceData.h b/source/RobotAPI/libraries/armem/core/io/DiskInstanceData.h new file mode 100644 index 0000000000000000000000000000000000000000..f871aff98d06d43f51772b4641f460d3d519c479 --- /dev/null +++ b/source/RobotAPI/libraries/armem/core/io/DiskInstanceData.h @@ -0,0 +1,48 @@ +/* +* This file is part of ArmarX. +* +* ArmarX is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* ArmarX is distributed in the hope that it will be useful, but +* WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* @author Fabian Peller (fabian dot peller at kit dot edu) +* @copyright http://www.gnu.org/licenses/gpl-2.0.txt +* GNU General Public License +*/ + +#pragma once + +// STD/STL +#include <string> +#include <filesystem> + +// ArmarX +#include <RobotAPI/interface/aron.h> + +#include <RobotAPI/libraries/armem/core/Time.h> + + +namespace armarx::armem::io +{ + class DiskInstanceData + { + // static use only + DiskInstanceData() = delete; + + public: + static constexpr const char* DISK_READER_WRITER_DATA_FIELD = "__ARON_DATA"; + static constexpr const char* DISK_READER_WRITER_TIME_STORED_FIELD = "__WRITER_METADATA__TIME_STORED"; + static constexpr const char* DISK_READER_WRITER_TIME_CREATED_FIELD = "__ENTITY_METADATA__TIME_CREATED"; + static constexpr const char* DISK_READER_WRITER_TIME_SENT_FIELD = "__ENTITY_METADATA__TIME_SENT"; + static constexpr const char* DISK_READER_WRITER_TIME_ARRIVED_FIELD = "__ENTITY_METADATA__TIME_ARRIVED"; + static constexpr const char* DISK_READER_WRITER_CONFIDENCE_FIELD = "__ENTITY_METADATA__CONFIDENCE"; + }; +} diff --git a/source/RobotAPI/libraries/armem/core/io/DiskMemory.cpp b/source/RobotAPI/libraries/armem/core/io/DiskMemory.cpp new file mode 100644 index 0000000000000000000000000000000000000000..c1f1974de5b4a05be03cbf92cea2dd7519247245 --- /dev/null +++ b/source/RobotAPI/libraries/armem/core/io/DiskMemory.cpp @@ -0,0 +1,202 @@ +/* +* This file is part of ArmarX. +* +* ArmarX is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* ArmarX is distributed in the hope that it will be useful, but +* WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* @author Fabian Peller (fabian dot peller at kit dot edu) +* @copyright http://www.gnu.org/licenses/gpl-2.0.txt +* GNU General Public License +*/ + +#include "DiskMemory.h" + + +namespace armarx::armem::io +{ + // copy + DiskMemory::DiskMemory(const DiskMemory& x): + DiskTypedEntityContainer(x.storagePath, x.reader), + diskCoreSegments(x.diskCoreSegments) + { + } + + // load on startup + DiskMemory::DiskMemory(const std::filesystem::path& loadFrom, const DiskReaderPtr& r) : + DiskTypedEntityContainer(loadFrom, r) + { + //std::cout << "Create DiskMemory" << std::endl; + append(loadFrom, r); + } + + // write on startup + DiskMemory::DiskMemory(const Memory& m, const std::filesystem::path& storeAt, const DiskWriterPtr& w) : + DiskTypedEntityContainer(storeAt, w->getCorrespondingDiskReader()) + { + //std::cout << "Create DiskMemory" << std::endl; + append(m, storeAt, w); + } + + // operators + std::string DiskMemory::toString() const + { + std::string endl = "\n"; + std::string tab = " "; + + std::stringstream ss; + ss << "{" << std::endl; + for (const auto& [key, p] : diskCoreSegments) + { + ss << tab << key << ":" << endl; + for (const auto& l : simox::alg::split(p.toString(), endl, false)) + { + ss << tab << l << endl; + } + } + ss << "}" << endl; + return ss.str(); + } + + DiskMemory& DiskMemory::operator=(const DiskMemory& x) + { + storagePath = x.storagePath; + reader = x.reader; + diskCoreSegments = x.diskCoreSegments; + return *this; + } + + aron::typenavigator::ObjectNavigatorPtr DiskMemory::getStoredObjectType() const + { + //std::cout << "DiskMemory: readStoredObjectType" << std::endl; + std::filesystem::path t = storagePath / (std::string(TYPE_FILENAME) + "." + reader->getTypeFileSuffix()); + return reader->readTypeInstance(t); + } + + bool DiskMemory::hasCoreSegment(const std::string& key) const + { + return diskCoreSegments.find(key) != diskCoreSegments.end(); + } + + DiskCoreSegment DiskMemory::getCoreSegment(const std::string& key) const + { + if (!hasCoreSegment(key)) + { + throw error::InvalidArgument("key", "DiskMemory::getCoreSegment", "The coresegment does not exist."); + } + return diskCoreSegments.at(key); + } + + const std::map<std::string, DiskCoreSegment>& DiskMemory::getCoreSegments() const + { + return diskCoreSegments; + } + + void DiskMemory::append(const Memory& m, const std::filesystem::path& storeAt, const DiskWriterPtr& w) + { + if (storeAt != storagePath) + { + throw error::ArMemError("Can not append a different path to a memory."); + } + + if (!std::filesystem::is_directory(storeAt)) + { + throw error::PathNotADirectory(storeAt, "Can not store a memory at this place."); + } + + initializeIf(storeAt, w->getCorrespondingDiskReader()); + + for (const auto& [key, p] : m.coreSegments) + { + std::filesystem::path pStoreAt = storeAt / key; + if (!std::filesystem::is_directory(pStoreAt)) + { + std::filesystem::create_directory(pStoreAt); + } + + DiskCoreSegment d(p, pStoreAt, w); + insert(key, d); + } + } + + void DiskMemory::append(const std::filesystem::path& loadFrom, const DiskReaderPtr& r) + { + if (loadFrom != storagePath) + { + throw error::ArMemError("Can not append a different path to a memory."); + } + + if (!std::filesystem::is_directory(loadFrom)) + { + throw error::PathNotADirectory(loadFrom, "Can not load a memory from this place."); + } + + initializeIf(loadFrom, r); + + for (const auto& p : std::filesystem::directory_iterator(loadFrom)) + { + if (!std::filesystem::is_directory(p)) + { + continue; + } + + std::string key = p.path().filename(); + DiskCoreSegment x(p, r); + insert(key, x); + } + } + + void DiskMemory::append(const DiskMemory& d) + { + if (initialized && d.storagePath != storagePath) + { + throw error::ArMemError("Can not append a diskmemory with different path to a memory."); + } + + initializeIf(d.storagePath, d.reader); + + for (const auto& [key, p] : d.diskCoreSegments) + { + insert(key, p); + } + } + + void DiskMemory::insert(const std::string& key, const DiskCoreSegment& p) + { + if (storagePath != p.getStoragePath().parent_path()) + { + throw error::ArMemError("Could not insert a coresegment with different parent path than memory."); + } + + if (hasCoreSegment(key)) + { + diskCoreSegments.at(key).append(p); + } + else + { + diskCoreSegments.insert(std::make_pair(key, p)); + } + } + + Memory DiskMemory::toMemory() const + { + // converts the stored references to a real Memory + //std::cout << "toMemory" << std::endl; + Memory s; + for (const auto& [key, p] : diskCoreSegments) + { + auto x = p.toCoreSegment(); + x.name() = key; + s.addCoreSegment(x); + } + return s; + } +} diff --git a/source/RobotAPI/libraries/armem/core/io/DiskMemory.h b/source/RobotAPI/libraries/armem/core/io/DiskMemory.h new file mode 100644 index 0000000000000000000000000000000000000000..536e793c51942f9776ced5220e4a70af56d3d6c9 --- /dev/null +++ b/source/RobotAPI/libraries/armem/core/io/DiskMemory.h @@ -0,0 +1,79 @@ +/* +* This file is part of ArmarX. +* +* ArmarX is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* ArmarX is distributed in the hope that it will be useful, but +* WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* @author Fabian Peller (fabian dot peller at kit dot edu) +* @copyright http://www.gnu.org/licenses/gpl-2.0.txt +* GNU General Public License +*/ + +#pragma once + +// STD/STL +#include <filesystem> +#include <map> +#include <string> +#include <vector> + +// BaseClass +#include "detail/DiskTypedEntityContainer.h" + +// ArmarX +#include "../Memory.h" +#include "DiskCoreSegment.h" + +namespace armarx::armem::io +{ + class DiskMemory : + virtual public DiskTypedEntityContainer + { + using aoType = aron::typenavigator::ObjectNavigatorPtr; + + public: + DiskMemory() = default; + + // copy + DiskMemory(const DiskMemory&); + + // load on startup + DiskMemory(const std::filesystem::path&, const DiskReaderPtr&); + + // write on startup + DiskMemory(const Memory&, const std::filesystem::path&, const DiskWriterPtr&); + + // operators + std::string toString() const; + DiskMemory& operator=(const DiskMemory&); + + // virtual + virtual aron::typenavigator::ObjectNavigatorPtr getStoredObjectType() const override; + + // public methods + bool hasCoreSegment(const std::string&) const; + + DiskCoreSegment getCoreSegment(const std::string&) const; + const std::map<std::string, DiskCoreSegment>& getCoreSegments() const; + + Memory toMemory() const; + + void append(const Memory&, const std::filesystem::path&, const DiskWriterPtr&); + void append(const std::filesystem::path&, const DiskReaderPtr&); + void append(const DiskMemory&); + + void insert(const std::string& key, const DiskCoreSegment& p); + + private: + std::map<std::string, DiskCoreSegment> diskCoreSegments; + }; +} diff --git a/source/RobotAPI/libraries/armem/core/io/DiskProviderSegment.cpp b/source/RobotAPI/libraries/armem/core/io/DiskProviderSegment.cpp new file mode 100644 index 0000000000000000000000000000000000000000..d5475182666465f723a6eea62065d3276c648dfa --- /dev/null +++ b/source/RobotAPI/libraries/armem/core/io/DiskProviderSegment.cpp @@ -0,0 +1,186 @@ +#include "DiskProviderSegment.h" + +#include "DiskCoreSegment.h" + +namespace armarx::armem::io +{ + // copy + DiskProviderSegment::DiskProviderSegment(const DiskProviderSegment& x): + DiskTypedEntityContainer(x.storagePath, x.reader), + diskEntities(x.diskEntities) + { + } + + // load + DiskProviderSegment::DiskProviderSegment(const std::filesystem::path& loadFrom, const DiskReaderPtr& r) : + DiskTypedEntityContainer(loadFrom, r) + { + //std::cout << "Create DiskProviderSegment" << std::endl; + append(loadFrom, r); + } + + // store + DiskProviderSegment::DiskProviderSegment(const ProviderSegment& c, const std::filesystem::path& storeAt, const DiskWriterPtr& w) : + DiskTypedEntityContainer(storeAt, w->getCorrespondingDiskReader()) + { + //std::cout << "Create DiskProviderSegment" << std::endl; + append(c, storeAt, w); + } + + // operators + std::string DiskProviderSegment::toString() const + { + std::string endl = "\n"; + std::string tab = " "; + + std::stringstream ss; + ss << "{" << std::endl; + for (const auto& [key, p] : diskEntities) + { + ss << tab << key << ":" << endl; + for (const auto& l : simox::alg::split(p.toString(), endl, false)) + { + ss << tab << l << endl; + } + } + ss << "}" << endl; + return ss.str(); + } + + DiskProviderSegment& DiskProviderSegment::operator=(const DiskProviderSegment& x) + { + storagePath = x.storagePath; + reader = x.reader; + diskEntities = x.diskEntities; + return *this; + } + + bool DiskProviderSegment::hasEntity(const std::string& key) const + { + return diskEntities.find(key) != diskEntities.end(); + } + + DiskEntity DiskProviderSegment::getEntity(const std::string& key) const + { + if (!hasEntity(key)) + { + throw error::InvalidArgument("key", "DiskProviderSegment::getEntity", "The entity does not exist."); + } + return diskEntities.at(key); + } + + const std::map<std::string, DiskEntity>& DiskProviderSegment::getEntities() const + { + return diskEntities; + } + + void DiskProviderSegment::append(const ProviderSegment& c, const std::filesystem::path& storeAt, const DiskWriterPtr& w) + { + if (!std::filesystem::is_directory(storeAt)) + { + throw error::PathNotADirectory(storeAt, ""); + } + + initializeIf(storeAt, w->getCorrespondingDiskReader()); + + for (const auto& [key, p] : c.entities) + { + std::filesystem::path pStoreAt = storeAt / key; + if (!std::filesystem::is_directory(pStoreAt)) + { + std::filesystem::create_directory(pStoreAt); + } + + if (c.aronType() != nullptr) + { + std::filesystem::path typeStoragePath = getStoragePath() / (std::string(TYPE_FILENAME) + "." + w->getTypeFileSuffix()); + w->writeTypeInstance(c.aronType(), typeStoragePath); + } + + DiskEntity d(p, pStoreAt, w); + if (auto it = diskEntities.find(key); it == diskEntities.end()) + { + diskEntities.insert(std::make_pair(key, d)); + } + else + { + it->second.append(d); + } + } + } + + void DiskProviderSegment::append(const std::filesystem::path& loadFrom, const DiskReaderPtr& r) + { + if (loadFrom != storagePath) + { + throw error::ArMemError("Can not append a different path to a providersegment."); + } + + if (!std::filesystem::is_directory(loadFrom)) + { + throw error::PathNotADirectory(loadFrom, "Can not load a providersegment from this place."); + } + + initializeIf(loadFrom, r); + + for (const auto& p : std::filesystem::directory_iterator(loadFrom)) + { + if (!std::filesystem::is_directory(p)) + { + continue; + } + + std::string key = p.path().filename(); + DiskEntity x(p, r); + insert(key, x); + } + } + + void DiskProviderSegment::append(const DiskProviderSegment& d) + { + if (d.storagePath != storagePath) + { + throw error::ArMemError("Can not append a diskmemory with different path to a providersegment."); + } + + initializeIf(d.storagePath, d.reader); + + for (const auto& [key, p] : d.diskEntities) + { + insert(key, p); + } + } + + void DiskProviderSegment::insert(const std::string& key, const DiskEntity& p) + { + if (hasEntity(key)) + { + diskEntities.at(key).append(p); + } + else + { + diskEntities.insert(std::make_pair(key, p)); + } + } + + ProviderSegment DiskProviderSegment::toProviderSegment(const aoType& mType, const aoType& cType) const + { + // converts the stored references to a real ProviderSegment + //std::cout << "toProviderSegment" << std::endl; + ProviderSegment s; + for (const auto& [key, p] : diskEntities) + { + auto x = p.toEntity(mType, cType, getStoredObjectType()); + x.name() = key; + s.addEntity(x); + } + return s; + } + + aron::typenavigator::ObjectNavigatorPtr DiskProviderSegment::getStoredObjectType() const + { + //std::cout << "DiskProviderSegment: readStoredObjectType" << std::endl; + std::filesystem::path t = storagePath / (std::string(TYPE_FILENAME) + "." + reader->getTypeFileSuffix()); + return reader->readTypeInstance(t); + } +} diff --git a/source/RobotAPI/libraries/armem/core/io/DiskProviderSegment.h b/source/RobotAPI/libraries/armem/core/io/DiskProviderSegment.h new file mode 100644 index 0000000000000000000000000000000000000000..293d2de8c24faa4c37422aa46596e1892b9e4490 --- /dev/null +++ b/source/RobotAPI/libraries/armem/core/io/DiskProviderSegment.h @@ -0,0 +1,80 @@ +/* +* This file is part of ArmarX. +* +* ArmarX is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* ArmarX is distributed in the hope that it will be useful, but +* WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* @author Fabian Peller (fabian dot peller at kit dot edu) +* @copyright http://www.gnu.org/licenses/gpl-2.0.txt +* GNU General Public License +*/ + +#pragma once + +// STD/STL +#include <map> +#include <string> +#include <vector> + +// BaseClass +#include "detail/DiskTypedEntityContainer.h" + +// ArmarX +#include "../ProviderSegment.h" +#include "DiskEntity.h" + + +namespace armarx::armem::io +{ + + class DiskProviderSegment : + virtual public DiskTypedEntityContainer + { + using aoType = aron::typenavigator::ObjectNavigatorPtr; + + public: + DiskProviderSegment() = default; + + // copy + DiskProviderSegment(const DiskProviderSegment&); + + // load + DiskProviderSegment(const std::filesystem::path&, const DiskReaderPtr&); + + // store + DiskProviderSegment(const ProviderSegment&, const std::filesystem::path&, const DiskWriterPtr&); + + // operators + std::string toString() const; + DiskProviderSegment& operator=(const DiskProviderSegment&); + + // virtual + virtual aron::typenavigator::ObjectNavigatorPtr getStoredObjectType() const override; + + // public methods + bool hasEntity(const std::string&) const; + + DiskEntity getEntity(const std::string&) const; + const std::map<std::string, DiskEntity>& getEntities() const; + + ProviderSegment toProviderSegment(const aoType& mType = nullptr, const aoType& cType = nullptr) const; + + void append(const ProviderSegment&, const std::filesystem::path&, const DiskWriterPtr&); + void append(const std::filesystem::path&, const DiskReaderPtr&); + void append(const DiskProviderSegment&); + + void insert(const std::string& key, const DiskEntity&); + + private: + std::map<std::string, DiskEntity> diskEntities; + }; +} diff --git a/source/RobotAPI/libraries/armem/core/io/DiskReader/DiskReader.cpp b/source/RobotAPI/libraries/armem/core/io/DiskReader/DiskReader.cpp deleted file mode 100644 index 08584369d6f745f7c0203497a531cd2e133319c2..0000000000000000000000000000000000000000 --- a/source/RobotAPI/libraries/armem/core/io/DiskReader/DiskReader.cpp +++ /dev/null @@ -1,194 +0,0 @@ -/* -* This file is part of ArmarX. -* -* ArmarX is free software; you can redistribute it and/or modify -* it under the terms of the GNU General Public License version 2 as -* published by the Free Software Foundation. -* -* ArmarX is distributed in the hope that it will be useful, but -* WITHOUT ANY WARRANTY; without even the implied warranty of -* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -* GNU General Public License for more details. -* -* You should have received a copy of the GNU General Public License -* along with this program. If not, see <http://www.gnu.org/licenses/>. -* -* @author Fabian Peller (fabian dot peller at kit dot edu) -* @copyright http://www.gnu.org/licenses/gpl-2.0.txt -* GNU General Public License -*/ - -#include "DiskReader.h" - -#include <sstream> -#include <fstream> -#include <iostream> - -// ArmarX -#include <RobotAPI/interface/aron.h> -#include <RobotAPI/libraries/aron/core/navigator/data/AllNavigators.h> -#include <RobotAPI/libraries/aron/core/navigator/type/AllNavigators.h> - -#include <RobotAPI/libraries/aron/core/io/dataIO/converter/Converter.h> -#include <RobotAPI/libraries/aron/core/io/dataIO/writer/navigator/NavigatorWriter.h> - -#include <RobotAPI/libraries/aron/core/io/typeIO/converter/Converter.h> -#include <RobotAPI/libraries/aron/core/io/typeIO/writer/navigator/NavigatorWriter.h> - -#include <RobotAPI/libraries/armem/core/error.h> - - -namespace armarx::armem::io -{ - - FileSystemLookupMemory DiskReader::readMemoryStructureFromDisk() - { - FileSystemLookupMemory ret; - - for (const auto& memoryFolder : std::filesystem::directory_iterator(rootPath)) - { - if (!std::filesystem::is_directory(memoryFolder)) - { - continue; - } - - std::string folderName = memoryFolder.path().filename(); - FileSystemLookupMemory tmp = readMemoryStructureFromDisk(folderName); - ret.merge(tmp); - } - return ret; - } - - FileSystemLookupMemory DiskReader::readMemoryStructureFromDisk(const std::string& memoryFolderName) - { - FileSystemLookupMemory ret; - - std::filesystem::path p = rootPath / memoryFolderName; - if (!std::filesystem::is_directory(p)) - { - return ret; - } - - for (const auto& coreSegmentFolder : std::filesystem::directory_iterator(p)) - { - if (!std::filesystem::is_directory(coreSegmentFolder)) - { - continue; - } - std::string coreSegmentName = coreSegmentFolder.path().filename(); - for (const auto& providerSegmentFolder : std::filesystem::directory_iterator(coreSegmentFolder.path())) - { - if (!std::filesystem::is_directory(providerSegmentFolder)) - { - continue; - } - std::string providerSegmentName = providerSegmentFolder.path().filename(); - for (const auto& entityFolder : std::filesystem::directory_iterator(providerSegmentFolder.path())) - { - if (!std::filesystem::is_directory(entityFolder)) - { - continue; - } - std::string entityName = entityFolder.path().filename(); - for (const auto& entityHistoryFolder : std::filesystem::directory_iterator(entityFolder.path())) - { - if (!std::filesystem::is_directory(entityHistoryFolder)) - { - continue; - } - Time entityTimestamp = armem::timeFromStringMicroSeconds(entityHistoryFolder.path().filename()); - - // TODO: make this relative to amount of files in folder - for (unsigned int i = 0; i < 10000; ++i) - { - std::filesystem::path entityInstance = entityHistoryFolder / std::filesystem::path(std::to_string(i) + getEntityInstanceSuffix()); - if (!std::filesystem::is_regular_file(entityInstance)) - { - break; - } - DiskMemory& mem = ret.memoryLookupTable[memoryFolderName]; - DiskCoreSegment& mem_core = mem[coreSegmentName]; - DiskProviderSegment& mem_prov = mem_core[providerSegmentName]; - DiskEntity& mem_entity = mem_prov[entityName]; - DiskEntitySnapshot& mem_entity_history = mem_entity[entityTimestamp]; - - mem_entity_history.push_back(entityInstance); - } - } - } - } - } - return ret; - } - - EntityInstance DiskReader::readSingleInstanceFromDisk(const MemoryID& id, const aron::typenavigator::NavigatorPtr& expectedStructure) const - { - std::filesystem::path p = rootPath / (id.str() + getEntityInstanceSuffix()); - return readSingleInstanceFromDisk(p, expectedStructure); - } - - EntityInstance DiskReader::readSingleInstanceFromDisk(const std::filesystem::path& p, const aron::typenavigator::NavigatorPtr& expectedStructure) const - { - if (!std::filesystem::is_regular_file(p)) - { - throw error::PathNotARegularFile(p.string(), "During readSingleInstanceFromDisk tried to read an entityInstance from a non-file path."); - } - - std::ifstream ifs(p); - std::string file_content((std::istreambuf_iterator<char>(ifs)), (std::istreambuf_iterator<char>())); - - aron::datanavigator::DictNavigatorPtr dictdata = getStringAsDataNavigator(file_content, expectedStructure); - return unwrapData(dictdata); - } - - aron::typenavigator::ObjectNavigatorPtr DiskReader::readSingleTypeInformationFromDisk(const MemoryID& id) const - { - std::filesystem::path p = rootPath / id.str() / (id.getLeafItem() + getTypeSuffix()); - return readSingleTypeInformationFromDisk(p); - } - - aron::typenavigator::ObjectNavigatorPtr DiskReader::readSingleTypeInformationFromDisk(const std::filesystem::path& p) const - { - if (!std::filesystem::is_regular_file(p)) - { - return nullptr; - } - - std::ifstream ifs(p); - std::string file_content((std::istreambuf_iterator<char>(ifs)), (std::istreambuf_iterator<char>())); - - aron::typenavigator::ObjectNavigatorPtr objecttype = getStringAsTypeNavigator(file_content); - return objecttype; - } - - EntityInstance DiskReader::unwrapData(const aron::datanavigator::DictNavigatorPtr& dataWrapped) const - { - EntityInstance e; - EntityInstanceMetadata& metadata = e.metadata(); - - aron::datanavigator::DictNavigatorPtr data = aron::datanavigator::DictNavigator::DynamicCastAndCheck(dataWrapped->getElement(DISK_READER_WRITER_DATA_FIELD)); - e.setData(data); - - // not used right now - //aron::datanavigator::LongNavigatorPtr timeWrapped = aron::datanavigator::LongNavigator::DynamicCastAndCheck(dataWrapped->getElement(DISK_READER_WRITER_TIME_WRAPPED_FIELD)); - - aron::datanavigator::LongNavigatorPtr timeCreated = aron::datanavigator::LongNavigator::DynamicCastAndCheck(dataWrapped->getElement(DISK_READER_WRITER_TIME_CREATED_FIELD)); - metadata.timeCreated = Time::microSeconds(timeCreated->toAronLongPtr()->value); - - aron::datanavigator::LongNavigatorPtr timeSent = aron::datanavigator::LongNavigator::DynamicCastAndCheck(dataWrapped->getElement(DISK_READER_WRITER_TIME_SENT_FIELD)); - metadata.timeSent = Time::microSeconds(timeSent->toAronLongPtr()->value); - - aron::datanavigator::LongNavigatorPtr timeArrived = aron::datanavigator::LongNavigator::DynamicCastAndCheck(dataWrapped->getElement(DISK_READER_WRITER_TIME_ARRIVED_FIELD)); - metadata.timeArrived = Time::microSeconds(timeArrived->toAronLongPtr()->value); - - aron::datanavigator::DoubleNavigatorPtr confidence = aron::datanavigator::DoubleNavigator::DynamicCastAndCheck(dataWrapped->getElement(DISK_READER_WRITER_CONFIDENCE_FIELD)); - metadata.confidence = static_cast<float>(confidence->toAronDoublePtr()->value); - - return e; - } - - aron::typenavigator::ObjectNavigatorPtr DiskReader::unwrapType(const aron::typenavigator::ObjectNavigatorPtr& t) const - { - return aron::typenavigator::ObjectNavigator::DynamicCastAndCheck(t->getMemberType(DISK_READER_WRITER_DATA_FIELD)); - } -} diff --git a/source/RobotAPI/libraries/armem/core/io/DiskReaderWriter.cpp b/source/RobotAPI/libraries/armem/core/io/DiskReaderWriter.cpp deleted file mode 100644 index 0929a3fc4d85a0efa44178cca02d218104956d48..0000000000000000000000000000000000000000 --- a/source/RobotAPI/libraries/armem/core/io/DiskReaderWriter.cpp +++ /dev/null @@ -1,69 +0,0 @@ -/* -* This file is part of ArmarX. -* -* ArmarX is free software; you can redistribute it and/or modify -* it under the terms of the GNU General Public License version 2 as -* published by the Free Software Foundation. -* -* ArmarX is distributed in the hope that it will be useful, but -* WITHOUT ANY WARRANTY; without even the implied warranty of -* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -* GNU General Public License for more details. -* -* You should have received a copy of the GNU General Public License -* along with this program. If not, see <http://www.gnu.org/licenses/>. -* -* @author Fabian Peller (fabian dot peller at kit dot edu) -* @copyright http://www.gnu.org/licenses/gpl-2.0.txt -* GNU General Public License -*/ - -#include "DiskReaderWriter.h" - -#include <RobotAPI/libraries/armem/core/error.h> - - -namespace armarx::armem::io -{ - - DiskReaderWriter::DiskReaderWriter(bool createIfNotExistent) : - DiskReaderWriter("/tmp/MemoryExport", createIfNotExistent) - {} - - DiskReaderWriter::DiskReaderWriter(const std::filesystem::path& rootPath, bool createIfNotExistent) : - rootPath(rootPath) - { - if (!std::filesystem::exists(rootPath.parent_path())) - { - throw error::PathDoesNotExist(rootPath.parent_path().string(), - "The parent path does not exist. At least this directory must exist!"); - } - - if (!std::filesystem::is_directory(rootPath.parent_path())) - { - throw error::PathDoesNotExist(rootPath.parent_path().string(), "The parent path is not a directory. It must be a directory."); - } - - if (!std::filesystem::exists(rootPath)) - { - if (createIfNotExistent) - { - std::filesystem::create_directory(rootPath); - } - else - { - throw error::PathDoesNotExist(rootPath.string(), "The path does not exist and a new folder should not be created!"); - } - } - - if (!std::filesystem::is_directory(rootPath)) - { - throw error::PathNotADirectory(rootPath.string(), "The Path is not valid. It points to a file instead of a folder!"); - } - } - - DiskReaderWriter::~DiskReaderWriter() - { - } - -} diff --git a/source/RobotAPI/libraries/armem/core/io/DiskReaderWriter.h b/source/RobotAPI/libraries/armem/core/io/DiskReaderWriter.h deleted file mode 100644 index eaed6011e162b5244e8ed4f97877d2b43c4f53c9..0000000000000000000000000000000000000000 --- a/source/RobotAPI/libraries/armem/core/io/DiskReaderWriter.h +++ /dev/null @@ -1,61 +0,0 @@ -/* -* This file is part of ArmarX. -* -* ArmarX is free software; you can redistribute it and/or modify -* it under the terms of the GNU General Public License version 2 as -* published by the Free Software Foundation. -* -* ArmarX is distributed in the hope that it will be useful, but -* WITHOUT ANY WARRANTY; without even the implied warranty of -* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -* GNU General Public License for more details. -* -* You should have received a copy of the GNU General Public License -* along with this program. If not, see <http://www.gnu.org/licenses/>. -* -* @author Fabian Peller (fabian dot peller at kit dot edu) -* @copyright http://www.gnu.org/licenses/gpl-2.0.txt -* GNU General Public License -*/ - -#pragma once - -// STD/STL -#include <string> -#include <filesystem> - -// ArmarX -#include <RobotAPI/interface/aron.h> - -#include <RobotAPI/libraries/armem/core/Time.h> - - -namespace armarx::armem::io -{ - class DiskReaderWriter - { - public: - DiskReaderWriter(bool createIfNotExistent); - DiskReaderWriter(const std::filesystem::path& rootPath, bool createIfNotExistent); - - virtual ~DiskReaderWriter(); - - - protected: - virtual std::string getEntityInstanceSuffix() const = 0; - virtual std::string getTypeSuffix() const = 0; - - protected: - std::filesystem::path rootPath; - - const std::string DISK_READER_WRITER_DATA_FIELD = "DATA"; - const std::string DISK_READER_WRITER_TIME_STORED_FIELD = "STORAGE_MANAGER_METADATA__TIME_STORED"; - const std::string DISK_READER_WRITER_TIME_CREATED_FIELD = "ENTITY_METADATA__TIME_CREATED"; - const std::string DISK_READER_WRITER_TIME_SENT_FIELD = "ENTITY_METADATA__TIME_SENT"; - const std::string DISK_READER_WRITER_TIME_ARRIVED_FIELD = "ENTITY_METADATA__TIME_ARRIVED"; - const std::string DISK_READER_WRITER_CONFIDENCE_FIELD = "ENTITY_METADATA__CONFIDENCE"; - - }; - - using DiskReaderWriterPtr = std::shared_ptr<DiskReaderWriter>; -} diff --git a/source/RobotAPI/libraries/armem/core/io/DiskWriter/DiskWriter.cpp b/source/RobotAPI/libraries/armem/core/io/DiskWriter/DiskWriter.cpp deleted file mode 100644 index 9168f8adf64313f17a21700a50d93113db60954c..0000000000000000000000000000000000000000 --- a/source/RobotAPI/libraries/armem/core/io/DiskWriter/DiskWriter.cpp +++ /dev/null @@ -1,303 +0,0 @@ -/* -* This file is part of ArmarX. -* -* ArmarX is free software; you can redistribute it and/or modify -* it under the terms of the GNU General Public License version 2 as -* published by the Free Software Foundation. -* -* ArmarX is distributed in the hope that it will be useful, but -* WITHOUT ANY WARRANTY; without even the implied warranty of -* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -* GNU General Public License for more details. -* -* You should have received a copy of the GNU General Public License -* along with this program. If not, see <http://www.gnu.org/licenses/>. -* -* @author Fabian Peller (fabian dot peller at kit dot edu) -* @copyright http://www.gnu.org/licenses/gpl-2.0.txt -* GNU General Public License -*/ - -// STD/STL -#include "DiskWriter.h" - -#include <fstream> -#include <iostream> - -// ArmarX -#include <RobotAPI/interface/aron.h> -#include <RobotAPI/libraries/aron/core/navigator/data/AllNavigators.h> -#include <RobotAPI/libraries/aron/core/navigator/type/AllNavigators.h> - -#include <RobotAPI/libraries/aron/core/io/dataIO/visitor/Visitor.h> -#include <RobotAPI/libraries/aron/core/io/dataIO/Writer.h> -#include <RobotAPI/libraries/aron/core/io/typeIO/visitor/Visitor.h> -#include <RobotAPI/libraries/aron/core/io/typeIO/Writer.h> - - -// BaseClass -#include "../DiskReaderWriter.h" -#include "../FileSystemLookupMemory.h" - -#include <RobotAPI/libraries/armem/core/Memory.h> -#include <RobotAPI/libraries/armem/core/CoreSegment.h> -#include <RobotAPI/libraries/armem/core/Entity.h> - - -namespace armarx::armem::io -{ - - DiskWriterReturnInformation DiskWriter::writeOnDisk(const Memory& m) - { - MemoryID id = m.id().getMemoryID(); - DiskWriterReturnInformation ret(id.memoryName); - - std::filesystem::path p = rootPath / id.str(); - if (!ensureDirectoryPathExists(p)) - { - ret.hasError = true; - return ret; - } - - for (const auto& [coreKey, coreSegment] : m.coreSegments) - { - MemoryID storeCore(id); - storeCore.coreSegmentName = coreKey; - DiskWriterReturnInformation other = writeOnDisk(storeCore, coreSegment); - ret.append(other); - } - return ret; - } - - DiskWriterReturnInformation DiskWriter::writeOnDisk(const MemoryID& i, const CoreSegment& s) - { - MemoryID id = i.getCoreSegmentID(); - DiskWriterReturnInformation ret(id.memoryName); - - std::filesystem::path p = rootPath / id.str(); - if (!ensureDirectoryPathExists(p)) - { - ret.coreSegmentsError.push_back(id.str()); - ret.hasError = true; - return ret; - } - - if (s.hasAronType()) - { - std::string val = getTypeAsString(wrapType(s.aronType())); - - std::filesystem::path coreSegmentProviderPath = rootPath / id.str() / (id.coreSegmentName + getTypeSuffix()); - std::ofstream ofs; - ofs.open(coreSegmentProviderPath); - ofs << val; - ofs.close(); - } - - for (const auto& [providerKey, providerSegment] : s.providerSegments) - { - MemoryID storeProvider(id); - storeProvider.providerSegmentName = providerKey; - DiskWriterReturnInformation other = writeOnDisk(storeProvider, providerSegment); - ret.append(other); - } - return ret; - } - - DiskWriterReturnInformation DiskWriter::writeOnDisk(const MemoryID& i, const ProviderSegment& s) - { - MemoryID id = i.getProviderSegmentID(); - DiskWriterReturnInformation ret(id.memoryName); - - std::filesystem::path p = rootPath / id.str(); - if (!ensureDirectoryPathExists(p)) - { - ret.providerSegmentsError.push_back(id.str()); - ret.hasError = true; - return ret; - } - - if (s.hasAronType()) - { - std::string val = getTypeAsString(wrapType(s.aronType())); - - std::filesystem::path providerSegmentProviderPath = rootPath / id.str() / (id.providerSegmentName + getTypeSuffix()); - std::ofstream ofs; - ofs.open(providerSegmentProviderPath); - ofs << val; - ofs.close(); - } - - for (const auto& [entityKey, entity] : s.entities) - { - MemoryID storeEntity(id); - storeEntity.entityName = entityKey; - DiskWriterReturnInformation other = writeOnDisk(storeEntity, entity); - ret.append(other); - } - return ret; - } - - DiskWriterReturnInformation DiskWriter::writeOnDisk(const MemoryID& i, const Entity& s) - { - MemoryID id = i.getEntityID(); - DiskWriterReturnInformation ret(id.memoryName); - - std::filesystem::path p = rootPath / id.str(); - if (!ensureDirectoryPathExists(p)) - { - ret.entitiesError.push_back(id.str()); - ret.hasError = true; - return ret; - } - - for (const auto& [ts, snapshot] : s.history) - { - MemoryID storeSnapshot(id); - storeSnapshot.timestamp = ts; - DiskWriterReturnInformation other = writeOnDisk(storeSnapshot, snapshot); - ret.append(other); - } - return ret; - } - - DiskWriterReturnInformation DiskWriter::writeOnDisk(const MemoryID& _id, const EntitySnapshot& s) - { - MemoryID id = _id.getEntitySnapshotID(); - DiskWriterReturnInformation ret(id.memoryName); - - std::filesystem::path p = rootPath / id.str(); - if (!ensureDirectoryPathExists(p)) - { - ret.historyTimestampsError.push_back(id.str()); - ret.hasError = true; - return ret; - } - - int i = 0; - for (const EntityInstance& instance : s.instances) - { - MemoryID storeInstance(id); - storeInstance.instanceIndex = i; - - std::filesystem::path entityElementPath = rootPath / (storeInstance.str() + getEntityInstanceSuffix()); - std::string val = getDataAsString(wrapData(instance)); - - if (filePathExists(entityElementPath)) - { - if (std::filesystem::is_directory(entityElementPath)) - { - ret.entityInstancesError.push_back(id.str()); - ret.hasError = true; - return ret; - } - //std::ifstream ifs(entityElementPath); - //std::string file_content((std::istreambuf_iterator<char>(ifs)), (std::istreambuf_iterator<char>())); - //if (file_content == val) - //{ - // // already written. skip - // continue; - //} - } - - std::ofstream ofs; - ofs.open(entityElementPath); - ofs << val; - ofs.close(); - ret.storedElements.memoryLookupTable[id.memoryName] - [id.coreSegmentName] - [id.providerSegmentName] - [id.entityName] - [id.timestamp].push_back(entityElementPath); - - i++; - } - return ret; - } - - aron::datanavigator::DictNavigatorPtr DiskWriter::wrapData(const EntityInstance& e) const - { - aron::datanavigator::DictNavigatorPtr dataWrapped(new aron::datanavigator::DictNavigator()); - dataWrapped->addElement(DISK_READER_WRITER_DATA_FIELD, e.data()); - - aron::datanavigator::LongNavigatorPtr timeWrapped(new aron::datanavigator::LongNavigator()); - timeWrapped->setValue(Time::now().toMicroSeconds()); - dataWrapped->addElement(DISK_READER_WRITER_TIME_STORED_FIELD, timeWrapped); - - - const EntityInstanceMetadata& metadata = e.metadata(); - aron::datanavigator::LongNavigatorPtr timeCreated(new aron::datanavigator::LongNavigator()); - timeCreated->setValue(metadata.timeCreated.toMicroSeconds()); - dataWrapped->addElement(DISK_READER_WRITER_TIME_CREATED_FIELD, timeCreated); - - aron::datanavigator::LongNavigatorPtr timeSent(new aron::datanavigator::LongNavigator()); - timeSent->setValue(metadata.timeSent.toMicroSeconds()); - dataWrapped->addElement(DISK_READER_WRITER_TIME_SENT_FIELD, timeSent); - - aron::datanavigator::LongNavigatorPtr timeArrived(new aron::datanavigator::LongNavigator()); - timeArrived->setValue(metadata.timeArrived.toMicroSeconds()); - dataWrapped->addElement(DISK_READER_WRITER_TIME_ARRIVED_FIELD, timeArrived); - - aron::datanavigator::DoubleNavigatorPtr confidence(new aron::datanavigator::DoubleNavigator()); - confidence->setValue(metadata.confidence); - dataWrapped->addElement(DISK_READER_WRITER_CONFIDENCE_FIELD, confidence); - - return dataWrapped; - } - - aron::typenavigator::ObjectNavigatorPtr DiskWriter::wrapType(const aron::typenavigator::ObjectNavigatorPtr& t) const - { - aron::typenavigator::ObjectNavigatorPtr typeWrapped(new aron::typenavigator::ObjectNavigator()); - typeWrapped->setObjectName(t->getName() + "__ltm_export"); - typeWrapped->addMemberType(DISK_READER_WRITER_DATA_FIELD, t); - - typeWrapped->addMemberType(DISK_READER_WRITER_TIME_STORED_FIELD, aron::typenavigator::LongNavigatorPtr(new aron::typenavigator::LongNavigator())); - typeWrapped->addMemberType(DISK_READER_WRITER_TIME_CREATED_FIELD, aron::typenavigator::LongNavigatorPtr(new aron::typenavigator::LongNavigator())); - typeWrapped->addMemberType(DISK_READER_WRITER_TIME_SENT_FIELD, aron::typenavigator::LongNavigatorPtr(new aron::typenavigator::LongNavigator())); - typeWrapped->addMemberType(DISK_READER_WRITER_TIME_ARRIVED_FIELD, aron::typenavigator::LongNavigatorPtr(new aron::typenavigator::LongNavigator())); - typeWrapped->addMemberType(DISK_READER_WRITER_CONFIDENCE_FIELD, aron::typenavigator::DoubleNavigatorPtr(new aron::typenavigator::DoubleNavigator())); - - return typeWrapped; - } - - bool DiskWriter::directoryPathExists(const std::filesystem::path& p) const - { - return std::filesystem::exists(p) && std::filesystem::is_directory(p); - } - - bool DiskWriter::ensureDirectoryPathExists(const std::filesystem::path& p) const - { - if (!std::filesystem::exists(p)) - { - return std::filesystem::create_directory(p); - } - return directoryPathExists(p); - } - - bool DiskWriter::filePathExists(const std::filesystem::path& p) const - { - return std::filesystem::exists(p) && std::filesystem::is_regular_file(p); - } - - - io::DiskWriterReturnInformation::DiskWriterReturnInformation(const std::string& m) : - memoryName(m) - { - } - - void io::DiskWriterReturnInformation::append(const io::DiskWriterReturnInformation& o) - { - if (memoryName != o.memoryName) - { - // The memory name must be equal - return; - } - - storedElements.merge(o.storedElements); - - coreSegmentsError.insert(coreSegmentsError.end(), o.coreSegmentsError.begin(), o.coreSegmentsError.end()); - providerSegmentsError.insert(providerSegmentsError.end(), o.providerSegmentsError.begin(), o.providerSegmentsError.end()); - entitiesError.insert(entitiesError.end(), o.entitiesError.begin(), o.entitiesError.end()); - historyTimestampsError.insert(historyTimestampsError.end(), o.historyTimestampsError.begin(), o.historyTimestampsError.end()); - entityInstancesError.insert(entityInstancesError.end(), o.entityInstancesError.begin(), o.entityInstancesError.end()); - } -} diff --git a/source/RobotAPI/libraries/armem/core/io/FileSystemLookupMemory.cpp b/source/RobotAPI/libraries/armem/core/io/FileSystemLookupMemory.cpp deleted file mode 100644 index ea9dc07dd048426f3cf4d57fa22790b27b15921d..0000000000000000000000000000000000000000 --- a/source/RobotAPI/libraries/armem/core/io/FileSystemLookupMemory.cpp +++ /dev/null @@ -1,217 +0,0 @@ -/* -* This file is part of ArmarX. -* -* ArmarX is free software; you can redistribute it and/or modify -* it under the terms of the GNU General Public License version 2 as -* published by the Free Software Foundation. -* -* ArmarX is distributed in the hope that it will be useful, but -* WITHOUT ANY WARRANTY; without even the implied warranty of -* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -* GNU General Public License for more details. -* -* You should have received a copy of the GNU General Public License -* along with this program. If not, see <http://www.gnu.org/licenses/>. -* -* @author Fabian Peller (fabian dot peller at kit dot edu) -* @copyright http://www.gnu.org/licenses/gpl-2.0.txt -* GNU General Public License -*/ - -#include "FileSystemLookupMemory.h" - - -namespace armarx::armem::io -{ - - DiskMemory FileSystemLookupMemory::getDiskMemory(const std::string& n) const - { - if (!hasMemory(n)) - { - throw error::ArMemError("Could not find a memory with name '" + n + "' in lookup memory."); - } - return memoryLookupTable.at(n); - } - - DiskMemory FileSystemLookupMemory::getDiskMemory(const MemoryID& id) const - { - if (!hasMemory(id)) - { - throw error::InvalidMemoryID(id, "MemoryName does not exist in lookup memory."); - } - return memoryLookupTable.at(id.memoryName); - } - - DiskCoreSegment FileSystemLookupMemory::getDiskCoreSegment(const MemoryID& id) const - { - if (!hasCoreSegment(id)) - { - throw error::InvalidMemoryID(id, "CoreSegmentName does not exist in lookup memory."); - } - return getDiskMemory(id).at(id.coreSegmentName); - } - - DiskProviderSegment FileSystemLookupMemory::getDiskProviderSegment(const MemoryID& id) const - { - if (!hasProviderSegment(id)) - { - throw error::InvalidMemoryID(id, "ProviderSegmentName does not exist in lookup memory."); - } - return getDiskCoreSegment(id).at(id.providerSegmentName); - } - - DiskEntity FileSystemLookupMemory::getDiskEntity(const MemoryID& id) const - { - if (!hasEntity(id)) - { - throw error::InvalidMemoryID(id, "EntityName does not exist in lookup memory."); - } - return getDiskProviderSegment(id).at(id.entityName); - } - - DiskEntitySnapshot FileSystemLookupMemory::getDiskEntitySnapshot(const MemoryID& id) const - { - if (!hasEntitySnapshot(id)) - { - throw error::InvalidMemoryID(id, "EntitySnapshotTimestamp does not exist in lookup memory."); - } - return getDiskEntity(id).at(id.timestamp); - } - - DiskEntityInstance FileSystemLookupMemory::getDiskEntityInstance(const MemoryID& id) const - { - if (!hasEntityInstance(id)) - { - throw error::InvalidMemoryID(id, "EntityInstanceIndex does not exist in lookup memory."); - } - return getDiskEntitySnapshot(id).at(id.instanceIndex); - } - - - bool FileSystemLookupMemory::hasMemory(const std::string& n) const - { - MemoryID id; - id.memoryName = n; - return hasMemory(id); - } - - bool FileSystemLookupMemory::hasMemory(const MemoryID& id) const - { - return id.hasMemoryName() && memoryLookupTable.find(id.memoryName) != memoryLookupTable.end(); - } - - bool FileSystemLookupMemory::hasCoreSegment(const MemoryID& id) const - { - if (hasMemory(id)) - { - const auto& m = getDiskMemory(id); - return id.hasCoreSegmentName() && m.find(id.coreSegmentName) != m.end(); - } - return false; - } - - bool FileSystemLookupMemory::hasProviderSegment(const MemoryID& id) const - { - if (hasCoreSegment(id)) - { - const auto& m = getDiskCoreSegment(id); - return id.hasProviderSegmentName() && m.find(id.providerSegmentName) != m.end(); - } - return false; - } - - bool FileSystemLookupMemory::hasEntity(const MemoryID& id) const - { - if (hasProviderSegment(id)) - { - const auto& m = getDiskProviderSegment(id); - return id.hasEntityName() && m.find(id.entityName) != m.end(); - } - return false; - } - - bool FileSystemLookupMemory::hasEntitySnapshot(const MemoryID& id) const - { - if (hasEntity(id)) - { - const auto& m = getDiskEntity(id); - return id.hasTimestamp() && m.find(id.timestamp) != m.end(); - } - return false; - } - - bool FileSystemLookupMemory::hasEntityInstance(const MemoryID& id) const - { - if (hasEntitySnapshot(id)) - { - const auto& m = getDiskEntitySnapshot(id); - return id.hasInstanceIndex() && m.size() >= (size_t) id.instanceIndex; - } - return false; - } - - - void FileSystemLookupMemory::merge(const FileSystemLookupMemory& m) - { - for (const auto& [memoryName, memory] : m.memoryLookupTable) - { - if (memoryLookupTable.find(memoryName) == memoryLookupTable.end()) - { - memoryLookupTable[memoryName] = memory; - continue; - } - - DiskMemory& lutMemory = memoryLookupTable[memoryName]; - for (const auto& [coreKey, coreSegment] : memory) - { - if (lutMemory.find(coreKey) == lutMemory.end()) - { - lutMemory[coreKey] = coreSegment; - continue; - } - - DiskCoreSegment& lutCoreSegment = lutMemory[coreKey]; - for (const auto& [providerKey, providerSegment] : coreSegment) - { - if (lutCoreSegment.find(providerKey) == lutCoreSegment.end()) - { - lutCoreSegment[providerKey] = providerSegment; - continue; - } - - DiskProviderSegment& lutProviderSegment = lutCoreSegment[providerKey]; - for (const auto& [entityKey, entity] : providerSegment) - { - if (lutProviderSegment.find(entityKey) == lutProviderSegment.end()) - { - lutProviderSegment[entityKey] = entity; - continue; - } - - DiskEntity& lutEntity = lutProviderSegment[entityKey]; - for (const auto& [entityHistoryTimestamp, entitySnapshot] : entity) - { - if (lutEntity.find(entityHistoryTimestamp) == lutEntity.end()) - { - lutEntity[entityHistoryTimestamp] = entitySnapshot; - continue; - } - - DiskEntitySnapshot& lutEntitySnapshot = lutEntity[entityHistoryTimestamp]; - //for (unsigned int i = 0; i < entitySnapshot.size(); ++i) - //{ - // // clear internal stored memory of that snapshot - // internalMemoryEntitySnapshot.clear(); - // internalMemoryEntitySnapshot.push_back(entitySnapshot[i]); - //} - // for now, simply overwrite all values since one history timestamp should not have two different snapshots - lutEntitySnapshot = entitySnapshot; - } - } - } - } - } - } - - -} diff --git a/source/RobotAPI/libraries/armem/core/io/FileSystemLookupMemory.h b/source/RobotAPI/libraries/armem/core/io/FileSystemLookupMemory.h deleted file mode 100644 index c3aa952f6e7895221db20f157f6fee83796722ea..0000000000000000000000000000000000000000 --- a/source/RobotAPI/libraries/armem/core/io/FileSystemLookupMemory.h +++ /dev/null @@ -1,68 +0,0 @@ -/* -* This file is part of ArmarX. -* -* ArmarX is free software; you can redistribute it and/or modify -* it under the terms of the GNU General Public License version 2 as -* published by the Free Software Foundation. -* -* ArmarX is distributed in the hope that it will be useful, but -* WITHOUT ANY WARRANTY; without even the implied warranty of -* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -* GNU General Public License for more details. -* -* You should have received a copy of the GNU General Public License -* along with this program. If not, see <http://www.gnu.org/licenses/>. -* -* @author Fabian Peller (fabian dot peller at kit dot edu) -* @copyright http://www.gnu.org/licenses/gpl-2.0.txt -* GNU General Public License -*/ - -#pragma once - -// STD/STL -#include <filesystem> -#include <map> -#include <string> -#include <vector> - -#include "../Time.h" -#include "../Memory.h" -#include "../error.h" - - -namespace armarx::armem::io -{ - using DiskEntityInstance = std::filesystem::path; // absolute paths to stored files - using DiskEntitySnapshot = std::vector<DiskEntityInstance>; - using DiskEntity = std::map<Time, DiskEntitySnapshot>; - using DiskProviderSegment = std::map<std::string, DiskEntity>; - using DiskCoreSegment = std::map<std::string, DiskProviderSegment>; - using DiskMemory = std::map<std::string, DiskCoreSegment>; - - - class FileSystemLookupMemory - { - public: - FileSystemLookupMemory() = default; - void merge(const FileSystemLookupMemory& m); - - DiskMemory getDiskMemory(const std::string&) const; - DiskMemory getDiskMemory(const MemoryID&) const; - DiskCoreSegment getDiskCoreSegment(const MemoryID&) const; - DiskProviderSegment getDiskProviderSegment(const MemoryID&) const; - DiskEntity getDiskEntity(const MemoryID&) const; - DiskEntitySnapshot getDiskEntitySnapshot(const MemoryID&) const; - DiskEntityInstance getDiskEntityInstance(const MemoryID&) const; - - bool hasMemory(const std::string&) const; - bool hasMemory(const MemoryID&) const; - bool hasCoreSegment(const MemoryID&) const; - bool hasProviderSegment(const MemoryID&) const; - bool hasEntity(const MemoryID&) const; - bool hasEntitySnapshot(const MemoryID&) const; - bool hasEntityInstance(const MemoryID&) const; - - std::map<std::string, DiskMemory> memoryLookupTable; - }; -} diff --git a/source/RobotAPI/libraries/armem/core/io/MemoryFileSystemStorage.cpp b/source/RobotAPI/libraries/armem/core/io/MemoryFileSystemStorage_OLD.cpp similarity index 100% rename from source/RobotAPI/libraries/armem/core/io/MemoryFileSystemStorage.cpp rename to source/RobotAPI/libraries/armem/core/io/MemoryFileSystemStorage_OLD.cpp diff --git a/source/RobotAPI/libraries/armem/core/io/MemoryFileSystemStorage.h b/source/RobotAPI/libraries/armem/core/io/MemoryFileSystemStorage_OLD.h similarity index 100% rename from source/RobotAPI/libraries/armem/core/io/MemoryFileSystemStorage.h rename to source/RobotAPI/libraries/armem/core/io/MemoryFileSystemStorage_OLD.h diff --git a/source/RobotAPI/libraries/armem/core/io/detail/DiskMemoryContainer.h b/source/RobotAPI/libraries/armem/core/io/detail/DiskMemoryContainer.h new file mode 100644 index 0000000000000000000000000000000000000000..c6477e73ffc4704dccadd44c9fd80546fc41cd47 --- /dev/null +++ b/source/RobotAPI/libraries/armem/core/io/detail/DiskMemoryContainer.h @@ -0,0 +1,46 @@ +/* +* This file is part of ArmarX. +* +* ArmarX is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* ArmarX is distributed in the hope that it will be useful, but +* WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* @author Fabian Peller (fabian dot peller at kit dot edu) +* @copyright http://www.gnu.org/licenses/gpl-2.0.txt +* GNU General Public License +*/ + +#pragma once + +// STD/STL +#include <map> +#include <string> +#include <vector> + +// BaseClass +#include "DiskMemoryItem.h" + +namespace armarx::armem::io +{ + + class DiskMemoryContainer : + public DiskMemoryItem + { + public: + DiskMemoryContainer() = default; + + // load + DiskMemoryContainer(const std::filesystem::path& p, const DiskReaderPtr& r) : + DiskMemoryItem(p, r) + { + } + }; +} diff --git a/source/RobotAPI/libraries/armem/core/io/detail/DiskMemoryItem.h b/source/RobotAPI/libraries/armem/core/io/detail/DiskMemoryItem.h new file mode 100644 index 0000000000000000000000000000000000000000..c4f8bf176a21022b729a578412cef8037e6440bb --- /dev/null +++ b/source/RobotAPI/libraries/armem/core/io/detail/DiskMemoryItem.h @@ -0,0 +1,73 @@ +/* +* This file is part of ArmarX. +* +* ArmarX is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* ArmarX is distributed in the hope that it will be useful, but +* WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* @author Fabian Peller (fabian dot peller at kit dot edu) +* @copyright http://www.gnu.org/licenses/gpl-2.0.txt +* GNU General Public License +*/ + +#pragma once + +// STD/STL +#include <map> +#include <string> +#include <vector> +#include <filesystem> + +// ArmarX +#include "../diskReader/DiskReader.h" +#include "../diskWriter/DiskWriter.h" + +namespace armarx::armem::io +{ + class DiskMemoryItem + { + + public: + DiskMemoryItem() = default; + + // load + DiskMemoryItem(const std::filesystem::path& p, const DiskReaderPtr& r) : + initialized(true), + reader(r), + storagePath(p) + { + } + + void initialize(const std::filesystem::path& p, const DiskReaderPtr& r) + { + reader = r; + storagePath = p; + } + + void initializeIf(const std::filesystem::path& p, const DiskReaderPtr& r) + { + if(!initialized) + { + initialize(p, r); + } + } + + const std::filesystem::path getStoragePath() const + { + return storagePath; + } + + protected: + bool initialized = false; + DiskReaderPtr reader; + std::filesystem::path storagePath; // replaces ID + }; +} diff --git a/source/RobotAPI/libraries/armem/core/io/detail/DiskTypedEntityContainer.h b/source/RobotAPI/libraries/armem/core/io/detail/DiskTypedEntityContainer.h new file mode 100644 index 0000000000000000000000000000000000000000..5c435c8f746c4345373f0881378cb4a87c24855f --- /dev/null +++ b/source/RobotAPI/libraries/armem/core/io/detail/DiskTypedEntityContainer.h @@ -0,0 +1,50 @@ +/* +* This file is part of ArmarX. +* +* ArmarX is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* ArmarX is distributed in the hope that it will be useful, but +* WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* @author Fabian Peller (fabian dot peller at kit dot edu) +* @copyright http://www.gnu.org/licenses/gpl-2.0.txt +* GNU General Public License +*/ + +#pragma once + +// STD/STL +#include <map> +#include <string> +#include <vector> + +// BaseClass +#include "DiskMemoryContainer.h" + +namespace armarx::armem::io +{ + + class DiskTypedEntityContainer : + public DiskMemoryContainer + { + public: + DiskTypedEntityContainer() = default; + + // load + DiskTypedEntityContainer(const std::filesystem::path& p, const DiskReaderPtr& r) : + DiskMemoryContainer(p, r) + { + } + + virtual aron::typenavigator::ObjectNavigatorPtr getStoredObjectType() const = 0; + + static constexpr const char* TYPE_FILENAME = "type"; + }; +} diff --git a/source/RobotAPI/libraries/armem/core/io/diskReader/DiskReader.cpp b/source/RobotAPI/libraries/armem/core/io/diskReader/DiskReader.cpp new file mode 100644 index 0000000000000000000000000000000000000000..318649fc6cfb88018f5b78e63988f33a3994ee38 --- /dev/null +++ b/source/RobotAPI/libraries/armem/core/io/diskReader/DiskReader.cpp @@ -0,0 +1,102 @@ +/* +* This file is part of ArmarX. +* +* ArmarX is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* ArmarX is distributed in the hope that it will be useful, but +* WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* @author Fabian Peller (fabian dot peller at kit dot edu) +* @copyright http://www.gnu.org/licenses/gpl-2.0.txt +* GNU General Public License +*/ + +#include "DiskReader.h" + +#include <sstream> +#include <fstream> +#include <iostream> + +// ArmarX +#include <RobotAPI/interface/aron.h> +#include <RobotAPI/libraries/aron/core/navigator/data/AllNavigators.h> +#include <RobotAPI/libraries/aron/core/navigator/type/AllNavigators.h> + +#include <RobotAPI/libraries/aron/core/io/dataIO/converter/Converter.h> +#include <RobotAPI/libraries/aron/core/io/dataIO/writer/navigator/NavigatorWriter.h> + +#include <RobotAPI/libraries/aron/core/io/typeIO/converter/Converter.h> +#include <RobotAPI/libraries/aron/core/io/typeIO/writer/navigator/NavigatorWriter.h> + +#include <RobotAPI/libraries/armem/core/error.h> + + +namespace armarx::armem::io +{ + EntityInstance DiskReader::readInstance(const std::filesystem::path& p, const aron::typenavigator::NavigatorPtr& expectedStructure) const + { + if (!std::filesystem::is_regular_file(p)) + { + throw error::PathNotARegularFile(p.string(), "During readSingleInstanceFromDisk tried to read an entityInstance from a non-file path."); + } + + std::ifstream ifs(p); + std::string file_content((std::istreambuf_iterator<char>(ifs)), (std::istreambuf_iterator<char>())); + + aron::datanavigator::DictNavigatorPtr dictdata = getStringAsDataNavigator(file_content, expectedStructure); + return unwrapData(dictdata); + } + + aron::typenavigator::ObjectNavigatorPtr DiskReader::readTypeInstance(const std::filesystem::path& p) const + { + //std::cout << "readTypeInstance" << std::endl; + if (!std::filesystem::is_regular_file(p)) + { + return nullptr; + } + + std::ifstream ifs(p); + std::string file_content((std::istreambuf_iterator<char>(ifs)), (std::istreambuf_iterator<char>())); + + aron::typenavigator::ObjectNavigatorPtr objecttype = getStringAsTypeNavigator(file_content); + return objecttype; + } + + EntityInstance DiskReader::unwrapData(const aron::datanavigator::DictNavigatorPtr& dataWrapped) const + { + EntityInstance e; + EntityInstanceMetadata& metadata = e.metadata(); + + aron::datanavigator::DictNavigatorPtr data = aron::datanavigator::DictNavigator::DynamicCastAndCheck(dataWrapped->getElement(DiskInstanceData::DISK_READER_WRITER_DATA_FIELD)); + e.setData(data); + + // not used right now + //aron::datanavigator::LongNavigatorPtr timeWrapped = aron::datanavigator::LongNavigator::DynamicCastAndCheck(dataWrapped->getElement(DiskInstanceData::DISK_READER_WRITER_TIME_WRAPPED_FIELD)); + + auto timeCreated = aron::datanavigator::LongNavigator::DynamicCastAndCheck(dataWrapped->getElement(DiskInstanceData::DISK_READER_WRITER_TIME_CREATED_FIELD)); + metadata.timeCreated = Time::microSeconds(timeCreated->toAronLongPtr()->value); + + auto timeSent = aron::datanavigator::LongNavigator::DynamicCastAndCheck(dataWrapped->getElement(DiskInstanceData::DISK_READER_WRITER_TIME_SENT_FIELD)); + metadata.timeSent = Time::microSeconds(timeSent->toAronLongPtr()->value); + + auto timeArrived = aron::datanavigator::LongNavigator::DynamicCastAndCheck(dataWrapped->getElement(DiskInstanceData::DISK_READER_WRITER_TIME_ARRIVED_FIELD)); + metadata.timeArrived = Time::microSeconds(timeArrived->toAronLongPtr()->value); + + auto confidence = aron::datanavigator::DoubleNavigator::DynamicCastAndCheck(dataWrapped->getElement(DiskInstanceData::DISK_READER_WRITER_CONFIDENCE_FIELD)); + metadata.confidence = static_cast<float>(confidence->toAronDoublePtr()->value); + + return e; + } + + aron::typenavigator::ObjectNavigatorPtr DiskReader::unwrapType(const aron::typenavigator::ObjectNavigatorPtr& t) const + { + return aron::typenavigator::ObjectNavigator::DynamicCastAndCheck(t->getMemberType(DiskInstanceData::DISK_READER_WRITER_DATA_FIELD)); + } +} diff --git a/source/RobotAPI/libraries/armem/core/io/DiskReader/DiskReader.h b/source/RobotAPI/libraries/armem/core/io/diskReader/DiskReader.h similarity index 67% rename from source/RobotAPI/libraries/armem/core/io/DiskReader/DiskReader.h rename to source/RobotAPI/libraries/armem/core/io/diskReader/DiskReader.h index 2ae252521b823e270533d2305a4af272b76bf944..4d01791c4cbae670886dd8e8bb3a60caea85e8fe 100644 --- a/source/RobotAPI/libraries/armem/core/io/DiskReader/DiskReader.h +++ b/source/RobotAPI/libraries/armem/core/io/diskReader/DiskReader.h @@ -25,14 +25,14 @@ #include <memory> #include <string> +// ArmarX #include <RobotAPI/libraries/aron/core/navigator/data/container/Dict.h> #include <RobotAPI/libraries/aron/core/navigator/type/Navigator.h> #include <RobotAPI/libraries/aron/core/navigator/type/container/Object.h> - #include <RobotAPI/libraries/armem/core/EntityInstance.h> -#include "../DiskReaderWriter.h" -#include "../FileSystemLookupMemory.h" +#include "../../Memory.h" +#include "../DiskInstanceData.h" namespace armarx::armem::io @@ -40,20 +40,14 @@ namespace armarx::armem::io class DiskReader; using DiskReaderPtr = std::shared_ptr<DiskReader>; - class DiskReader : virtual public DiskReaderWriter + class DiskReader { public: + EntityInstance readInstance(const std::filesystem::path&, const aron::typenavigator::NavigatorPtr& expectedStructure = nullptr) const; + aron::typenavigator::ObjectNavigatorPtr readTypeInstance(const std::filesystem::path&) const; - using DiskReaderWriter::DiskReaderWriter; - - FileSystemLookupMemory readMemoryStructureFromDisk(); - FileSystemLookupMemory readMemoryStructureFromDisk(const std::string&); - - EntityInstance readSingleInstanceFromDisk(const std::filesystem::path&, const aron::typenavigator::NavigatorPtr& expectedStructure = nullptr) const; - EntityInstance readSingleInstanceFromDisk(const MemoryID&, const aron::typenavigator::NavigatorPtr& expectedStructure = nullptr) const; - - aron::typenavigator::ObjectNavigatorPtr readSingleTypeInformationFromDisk(const std::filesystem::path&) const; - aron::typenavigator::ObjectNavigatorPtr readSingleTypeInformationFromDisk(const MemoryID&) const; + virtual std::string getDataFileSuffix() const = 0; + virtual std::string getTypeFileSuffix() const = 0; protected: EntityInstance unwrapData(const aron::datanavigator::DictNavigatorPtr&) const; diff --git a/source/RobotAPI/libraries/armem/core/io/DiskReader/NlohmannJSONDiskReader/NlohmannJSONDiskReader.cpp b/source/RobotAPI/libraries/armem/core/io/diskReader/NlohmannJSON/NlohmannJSONDiskReader.cpp similarity index 71% rename from source/RobotAPI/libraries/armem/core/io/DiskReader/NlohmannJSONDiskReader/NlohmannJSONDiskReader.cpp rename to source/RobotAPI/libraries/armem/core/io/diskReader/NlohmannJSON/NlohmannJSONDiskReader.cpp index 3742996cda7cf4f03a15615a5ba7a296dfeba591..aedc1f42d14750b8021f94fc1131408cdc7c475a 100644 --- a/source/RobotAPI/libraries/armem/core/io/DiskReader/NlohmannJSONDiskReader/NlohmannJSONDiskReader.cpp +++ b/source/RobotAPI/libraries/armem/core/io/diskReader/NlohmannJSON/NlohmannJSONDiskReader.cpp @@ -10,24 +10,11 @@ namespace armarx::armem::io { - - NlohmannJSONDiskReader::NlohmannJSONDiskReader(bool createFolder) : - DiskReaderWriter(createFolder), - DiskReader(createFolder) - { - } - - NlohmannJSONDiskReader::NlohmannJSONDiskReader(const std::string& rootPath, bool createFolder) : - DiskReaderWriter(rootPath, createFolder), - DiskReader(rootPath, createFolder) - { - } - aron::datanavigator::DictNavigatorPtr NlohmannJSONDiskReader::getStringAsDataNavigator(const std::string& s, const aron::typenavigator::NavigatorPtr& expectedStructure) const { aron::dataIO::reader::NlohmannJSONReader dataReader(s); aron::dataIO::writer::NavigatorWriter navWriter; - aron::dataIO::Converter::ConvertFromReader(dataReader, navWriter, expectedStructure); + aron::dataIO::Converter::ReadAndConvert(dataReader, navWriter, expectedStructure); return aron::datanavigator::DictNavigator::DynamicCastAndCheck(navWriter.getResult()); } @@ -35,7 +22,7 @@ namespace armarx::armem::io { aron::typeIO::reader::NlohmannJSONReader typeReader(s); aron::typeIO::writer::NavigatorWriter navWriter; - aron::typeIO::Converter::ConvertFromReader(typeReader, navWriter); + aron::typeIO::Converter::ReadAndConvert(typeReader, navWriter); return aron::typenavigator::ObjectNavigator::DynamicCastAndCheck(navWriter.getResult()); } } diff --git a/source/RobotAPI/libraries/armem/core/io/DiskReader/NlohmannJSONDiskReader/NlohmannJSONDiskReader.h b/source/RobotAPI/libraries/armem/core/io/diskReader/NlohmannJSON/NlohmannJSONDiskReader.h similarity index 82% rename from source/RobotAPI/libraries/armem/core/io/DiskReader/NlohmannJSONDiskReader/NlohmannJSONDiskReader.h rename to source/RobotAPI/libraries/armem/core/io/diskReader/NlohmannJSON/NlohmannJSONDiskReader.h index 6358d751b07fe395de0345bf06aa4af374b85289..39ac04b72ef4f469c15aa413df6e9fa0d2a761fa 100644 --- a/source/RobotAPI/libraries/armem/core/io/DiskReader/NlohmannJSONDiskReader/NlohmannJSONDiskReader.h +++ b/source/RobotAPI/libraries/armem/core/io/diskReader/NlohmannJSON/NlohmannJSONDiskReader.h @@ -36,8 +36,7 @@ namespace armarx::armem::io class NlohmannJSONDiskReader : virtual public DiskReader { public: - NlohmannJSONDiskReader(bool createFolder); - NlohmannJSONDiskReader(const std::string& rootPath, bool createFolder); + NlohmannJSONDiskReader() = default; protected: @@ -45,14 +44,14 @@ namespace armarx::armem::io const std::string&, const aron::typenavigator::NavigatorPtr& expectedStructure = nullptr) const override; aron::typenavigator::ObjectNavigatorPtr getStringAsTypeNavigator(const std::string& s) const override; - std::string getEntityInstanceSuffix() const override + std::string getDataFileSuffix() const override { - return ".data.json"; + return "data.json"; } - std::string getTypeSuffix() const override + std::string getTypeFileSuffix() const override { - return ".type.json"; + return "type.json"; } }; } diff --git a/source/RobotAPI/libraries/armem/core/io/diskWriter/DiskWriter.cpp b/source/RobotAPI/libraries/armem/core/io/diskWriter/DiskWriter.cpp new file mode 100644 index 0000000000000000000000000000000000000000..1256b77047339155c8fdc308408849d51d649830 --- /dev/null +++ b/source/RobotAPI/libraries/armem/core/io/diskWriter/DiskWriter.cpp @@ -0,0 +1,115 @@ +/* +* This file is part of ArmarX. +* +* ArmarX is free software; you can redistribute it and/or modify +* it under the terms of the GNU General Public License version 2 as +* published by the Free Software Foundation. +* +* ArmarX is distributed in the hope that it will be useful, but +* WITHOUT ANY WARRANTY; without even the implied warranty of +* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +* +* You should have received a copy of the GNU General Public License +* along with this program. If not, see <http://www.gnu.org/licenses/>. +* +* @author Fabian Peller (fabian dot peller at kit dot edu) +* @copyright http://www.gnu.org/licenses/gpl-2.0.txt +* GNU General Public License +*/ + +// STD/STL +#include "DiskWriter.h" + +#include <fstream> +#include <iostream> + +// ArmarX +#include <RobotAPI/interface/aron.h> +#include <RobotAPI/libraries/aron/core/navigator/data/AllNavigators.h> +#include <RobotAPI/libraries/aron/core/navigator/type/AllNavigators.h> + +#include <RobotAPI/libraries/aron/core/io/dataIO/visitor/Visitor.h> +#include <RobotAPI/libraries/aron/core/io/dataIO/Writer.h> +#include <RobotAPI/libraries/aron/core/io/typeIO/visitor/Visitor.h> +#include <RobotAPI/libraries/aron/core/io/typeIO/Writer.h> + + +// BaseClass +#include <RobotAPI/libraries/armem/core/Memory.h> +#include <RobotAPI/libraries/armem/core/CoreSegment.h> +#include <RobotAPI/libraries/armem/core/Entity.h> + + +namespace armarx::armem::io +{ + + void DiskWriter::writeInstance(const EntityInstance& c, const std::filesystem::path& p) + { + std::string val = getDataAsString(wrapData(c)); + + std::ofstream ofs; + ofs.open(p); + ofs << val; + ofs.close(); + } + + void DiskWriter::writeTypeInstance(const aron::typenavigator::ObjectNavigatorPtr& n, const std::filesystem::path& p) + { + if (n == nullptr) + { + return; + } + std::string val = getTypeAsString(wrapType(n)); + + std::ofstream ofs; + ofs.open(p); + ofs << val; + ofs.close(); + } + + aron::datanavigator::DictNavigatorPtr DiskWriter::wrapData(const EntityInstance& e) const + { + auto dataWrapped = std::make_shared<aron::datanavigator::DictNavigator>(); + dataWrapped->addElement(DiskInstanceData::DISK_READER_WRITER_DATA_FIELD, e.data()); + + auto timeWrapped = std::make_shared<aron::datanavigator::LongNavigator>(); + timeWrapped->setValue(Time::now().toMicroSeconds()); + dataWrapped->addElement(DiskInstanceData::DISK_READER_WRITER_TIME_STORED_FIELD, timeWrapped); + + + const EntityInstanceMetadata& metadata = e.metadata(); + auto timeCreated = std::make_shared<aron::datanavigator::LongNavigator>(); + timeCreated->setValue(metadata.timeCreated.toMicroSeconds()); + dataWrapped->addElement(DiskInstanceData::DISK_READER_WRITER_TIME_CREATED_FIELD, timeCreated); + + auto timeSent = std::make_shared<aron::datanavigator::LongNavigator>(); + timeSent->setValue(metadata.timeSent.toMicroSeconds()); + dataWrapped->addElement(DiskInstanceData::DISK_READER_WRITER_TIME_SENT_FIELD, timeSent); + + auto timeArrived = std::make_shared<aron::datanavigator::LongNavigator>(); + timeArrived->setValue(metadata.timeArrived.toMicroSeconds()); + dataWrapped->addElement(DiskInstanceData::DISK_READER_WRITER_TIME_ARRIVED_FIELD, timeArrived); + + auto confidence = std::make_shared<aron::datanavigator::DoubleNavigator>(); + confidence->setValue(metadata.confidence); + dataWrapped->addElement(DiskInstanceData::DISK_READER_WRITER_CONFIDENCE_FIELD, confidence); + + return dataWrapped; + } + + aron::typenavigator::ObjectNavigatorPtr DiskWriter::wrapType(const aron::typenavigator::ObjectNavigatorPtr& t) const + { + aron::typenavigator::ObjectNavigatorPtr typeWrapped(new aron::typenavigator::ObjectNavigator()); + typeWrapped->setObjectName(t->getObjectName() + "__ltm_export"); + typeWrapped->addMemberType(DiskInstanceData::DISK_READER_WRITER_DATA_FIELD, t); + + typeWrapped->addMemberType(DiskInstanceData::DISK_READER_WRITER_TIME_STORED_FIELD, std::make_shared<aron::typenavigator::LongNavigator>()); + typeWrapped->addMemberType(DiskInstanceData::DISK_READER_WRITER_TIME_CREATED_FIELD, std::make_shared<aron::typenavigator::LongNavigator>()); + typeWrapped->addMemberType(DiskInstanceData::DISK_READER_WRITER_TIME_SENT_FIELD, std::make_shared<aron::typenavigator::LongNavigator>()); + typeWrapped->addMemberType(DiskInstanceData::DISK_READER_WRITER_TIME_ARRIVED_FIELD, std::make_shared<aron::typenavigator::LongNavigator>()); + typeWrapped->addMemberType(DiskInstanceData::DISK_READER_WRITER_CONFIDENCE_FIELD, std::make_shared<aron::typenavigator::DoubleNavigator>()); + + return typeWrapped; + } +} diff --git a/source/RobotAPI/libraries/armem/core/io/DiskWriter/DiskWriter.h b/source/RobotAPI/libraries/armem/core/io/diskWriter/DiskWriter.h similarity index 52% rename from source/RobotAPI/libraries/armem/core/io/DiskWriter/DiskWriter.h rename to source/RobotAPI/libraries/armem/core/io/diskWriter/DiskWriter.h index c8b4e4541e341e23bab18f45cb956620178771c8..11e26a4fc0f8c3f56101bee0775750aa3ecad90b 100644 --- a/source/RobotAPI/libraries/armem/core/io/DiskWriter/DiskWriter.h +++ b/source/RobotAPI/libraries/armem/core/io/diskWriter/DiskWriter.h @@ -30,33 +30,26 @@ #include <RobotAPI/libraries/aron/core/navigator/type/Navigator.h> #include <RobotAPI/libraries/aron/core/navigator/type/container/Object.h> - -// BaseClass -#include "../DiskReaderWriter.h" -#include "../FileSystemLookupMemory.h" - -#include <RobotAPI/libraries/armem/core/Memory.h> +#include "../../Memory.h" +#include "../diskReader/DiskReader.h" +#include "../DiskInstanceData.h" namespace armarx::armem::io { - struct DiskWriterReturnInformation; - - class DiskWriter; using DiskWriterPtr = std::shared_ptr<DiskWriter>; - class DiskWriter : virtual public DiskReaderWriter + class DiskWriter { public: + void writeInstance(const EntityInstance&, const std::filesystem::path&); + void writeTypeInstance(const aron::typenavigator::ObjectNavigatorPtr&, const std::filesystem::path&); - using DiskReaderWriter::DiskReaderWriter; + virtual std::string getDataFileSuffix() const = 0; + virtual std::string getTypeFileSuffix() const = 0; - DiskWriterReturnInformation writeOnDisk(const Memory& m); - DiskWriterReturnInformation writeOnDisk(const MemoryID&, const CoreSegment&); - DiskWriterReturnInformation writeOnDisk(const MemoryID&, const ProviderSegment&); - DiskWriterReturnInformation writeOnDisk(const MemoryID&, const Entity&); - DiskWriterReturnInformation writeOnDisk(const MemoryID&, const EntitySnapshot&); + virtual DiskReaderPtr getCorrespondingDiskReader() const = 0; protected: aron::datanavigator::DictNavigatorPtr wrapData(const EntityInstance& e) const; @@ -64,28 +57,5 @@ namespace armarx::armem::io virtual std::string getDataAsString(const aron::datanavigator::DictNavigatorPtr&) const = 0; virtual std::string getTypeAsString(const aron::typenavigator::ObjectNavigatorPtr&) const = 0; - - bool directoryPathExists(const std::filesystem::path& p) const; - bool ensureDirectoryPathExists(const std::filesystem::path& p) const; - - bool filePathExists(const std::filesystem::path& p) const; - }; - - - struct DiskWriterReturnInformation - { - std::string memoryName = ""; - bool hasError = false; - - FileSystemLookupMemory storedElements; - std::vector<std::string> coreSegmentsError; - std::vector<std::string> providerSegmentsError; - std::vector<std::string> entitiesError; - std::vector<std::string> historyTimestampsError; - std::vector<std::string> entityInstancesError; - - DiskWriterReturnInformation(const std::string& m); - - void append(const DiskWriterReturnInformation& o); }; } diff --git a/source/RobotAPI/libraries/armem/core/io/DiskWriter/NlohmannJSONDiskWriter/NlohmannJSONDiskWriter.cpp b/source/RobotAPI/libraries/armem/core/io/diskWriter/NlohmannJSON/NlohmannJSONDiskWriter.cpp similarity index 60% rename from source/RobotAPI/libraries/armem/core/io/DiskWriter/NlohmannJSONDiskWriter/NlohmannJSONDiskWriter.cpp rename to source/RobotAPI/libraries/armem/core/io/diskWriter/NlohmannJSON/NlohmannJSONDiskWriter.cpp index a52253d8cdfe867195e3f595832746a7e312f0fc..22fe7a5a27b4f933011344e0797b84f47feb4c02 100644 --- a/source/RobotAPI/libraries/armem/core/io/DiskWriter/NlohmannJSONDiskWriter/NlohmannJSONDiskWriter.cpp +++ b/source/RobotAPI/libraries/armem/core/io/diskWriter/NlohmannJSON/NlohmannJSONDiskWriter.cpp @@ -8,29 +8,17 @@ namespace armarx::armem::io { - NlohmannJSONDiskWriter::NlohmannJSONDiskWriter(bool createFolder) : - DiskReaderWriter(createFolder), - DiskWriter(createFolder) - { - } - - NlohmannJSONDiskWriter::NlohmannJSONDiskWriter(const std::string& rootPath, bool createFolder) : - DiskReaderWriter(rootPath, createFolder), - DiskWriter(rootPath, createFolder) - { - } - std::string NlohmannJSONDiskWriter::getDataAsString(const aron::datanavigator::DictNavigatorPtr& aronDataNav) const { aron::dataIO::writer::NlohmannJSONWriter dataWriter; - aron::dataIO::Visitor::SetupWriterFromAronDataPtr(dataWriter, aronDataNav->getResult()); + aron::dataIO::Visitor::VisitAndSetup(dataWriter, aronDataNav); return dataWriter.getResult().dump(2); } std::string NlohmannJSONDiskWriter::getTypeAsString(const aron::typenavigator::ObjectNavigatorPtr& aronTypeNav) const { aron::typeIO::writer::NlohmannJSONWriter typeWriter; - aron::typeIO::Visitor::SetupWriterFromAronTypePtr(typeWriter, aronTypeNav->getResult()); + aron::typeIO::Visitor::VisitAndSetup(typeWriter, aronTypeNav); return typeWriter.getResult().dump(2); } } diff --git a/source/RobotAPI/libraries/armem/core/io/DiskWriter/NlohmannJSONDiskWriter/NlohmannJSONDiskWriter.h b/source/RobotAPI/libraries/armem/core/io/diskWriter/NlohmannJSON/NlohmannJSONDiskWriter.h similarity index 74% rename from source/RobotAPI/libraries/armem/core/io/DiskWriter/NlohmannJSONDiskWriter/NlohmannJSONDiskWriter.h rename to source/RobotAPI/libraries/armem/core/io/diskWriter/NlohmannJSON/NlohmannJSONDiskWriter.h index 67d35f01aa874f3c203d4ffffd5bd5691b237bb0..71b66a11ad15d6751e3918c54010b0136150268a 100644 --- a/source/RobotAPI/libraries/armem/core/io/DiskWriter/NlohmannJSONDiskWriter/NlohmannJSONDiskWriter.h +++ b/source/RobotAPI/libraries/armem/core/io/diskWriter/NlohmannJSON/NlohmannJSONDiskWriter.h @@ -27,6 +27,8 @@ // Base Class #include "../DiskWriter.h" +// ArmarX +#include "../../diskReader/NlohmannJSON/NlohmannJSONDiskReader.h" namespace armarx::armem::io { @@ -36,22 +38,25 @@ namespace armarx::armem::io class NlohmannJSONDiskWriter : virtual public DiskWriter { public: - NlohmannJSONDiskWriter(bool createFolder); - NlohmannJSONDiskWriter(const std::string& rootPath, bool createFolder); - + NlohmannJSONDiskWriter() = default; protected: std::string getDataAsString(const aron::datanavigator::DictNavigatorPtr&) const override; std::string getTypeAsString(const aron::typenavigator::ObjectNavigatorPtr&) const override; - std::string getEntityInstanceSuffix() const override + virtual DiskReaderPtr getCorrespondingDiskReader() const override + { + return std::make_shared<NlohmannJSONDiskReader>(); + } + + std::string getDataFileSuffix() const override { - return ".data.json"; + return "data.json"; } - std::string getTypeSuffix() const override + std::string getTypeFileSuffix() const override { - return ".type.json"; + return "type.json"; } }; } diff --git a/source/RobotAPI/libraries/armem/server/ComponentPlugin.cpp b/source/RobotAPI/libraries/armem/server/ComponentPlugin.cpp index de811a33125e672a0a57e266ef5ca9b59971b083..6caae72cf216edf6ef874c8392ffa1ec4aacf955 100644 --- a/source/RobotAPI/libraries/armem/server/ComponentPlugin.cpp +++ b/source/RobotAPI/libraries/armem/server/ComponentPlugin.cpp @@ -102,7 +102,6 @@ namespace armarx::armem::server // WRITING - data::AddSegmentsResult ComponentPluginUser::addSegments(const data::AddSegmentsInput& input, const Ice::Current&) { bool addCoreSegmentOnUsage = false; @@ -125,11 +124,25 @@ namespace armarx::armem::server // READING - armem::query::data::Result ComponentPluginUser::query(const armem::query::data::Input& input, const Ice::Current&) { std::scoped_lock lock(memoryMutex); return iceMemory.query(input); } + // LTM LOADING + data::StoreResult ComponentPluginUser::store(const data::StoreInput& input, const Ice::Current&) + { + std::scoped_lock lock(memoryMutex); + return iceMemory.store(input); + } + + + // LTM STORING + data::LoadResult ComponentPluginUser::load(const data::LoadInput& input, const Ice::Current&) + { + std::scoped_lock lock(memoryMutex); + return iceMemory.load(input); + } + } diff --git a/source/RobotAPI/libraries/armem/server/ComponentPlugin.h b/source/RobotAPI/libraries/armem/server/ComponentPlugin.h index ca0958b3c93203ef519c2c5311b71c1b0f54cd98..d7b5dcaebcf085042b10ff9992ee041296e69ac3 100644 --- a/source/RobotAPI/libraries/armem/server/ComponentPlugin.h +++ b/source/RobotAPI/libraries/armem/server/ComponentPlugin.h @@ -80,17 +80,28 @@ namespace armarx::armem::server virtual armem::query::data::Result query(const armem::query::data::Input& input, const Ice::Current& = Ice::emptyCurrent) override; + // LoadingInterface interface + data::StoreResult store(const data::StoreInput&, const Ice::Current& = Ice::emptyCurrent) override; + + + // StoringInterface interface + data::LoadResult load(const data::LoadInput&, const Ice::Current& = Ice::emptyCurrent) override; + + public: /// The actual memory. Memory memory; std::mutex memoryMutex; + io::DiskMemory diskMemory; + std::mutex diskMemoryMutex; + /// property defauls std::string memoryListenerDefaultName = "MemoryUpdates"; /// Helps connecting `memory` to ice. Used to handle Ice callbacks. - MemoryToIceAdapter iceMemory { &memory }; + MemoryToIceAdapter iceMemory { &memory, &diskMemory}; private: diff --git a/source/RobotAPI/libraries/armem/server/MemoryToIceAdapter.cpp b/source/RobotAPI/libraries/armem/server/MemoryToIceAdapter.cpp index 22c47eea2cd3c2e0121297f6d5b2e88f369ea3a3..895b76bf02f5c70f4758dd1d9ee7352f8bb335cc 100644 --- a/source/RobotAPI/libraries/armem/server/MemoryToIceAdapter.cpp +++ b/source/RobotAPI/libraries/armem/server/MemoryToIceAdapter.cpp @@ -6,11 +6,13 @@ #include "../core/ice_conversions.h" #include "query_proc/MemoryQueryProcessor.h" +#include "../core/io/diskWriter/NlohmannJSON/NlohmannJSONDiskWriter.h" +#include "../core/io/diskReader/NlohmannJSON/NlohmannJSONDiskReader.h" namespace armarx::armem::server { - MemoryToIceAdapter::MemoryToIceAdapter(Memory* memory) : memory(memory) + MemoryToIceAdapter::MemoryToIceAdapter(Memory* memory, io::DiskMemory* diskMemory) : memory(memory), diskMemory(diskMemory) { } @@ -23,7 +25,6 @@ namespace armarx::armem::server // WRITING - data::AddSegmentResult MemoryToIceAdapter::addSegment(const data::AddSegmentInput& input, bool addCoreSegments) { @@ -157,7 +158,6 @@ namespace armarx::armem::server // READING - armem::query::data::Result MemoryToIceAdapter::query(const armem::query::data::Input& input) { @@ -169,4 +169,32 @@ namespace armarx::armem::server return processor.process(input, *memory); } + // LTM LOADING + data::LoadResult MemoryToIceAdapter::load(const armem::data::LoadInput& input) + { + ARMARX_CHECK_NOT_NULL(diskMemory); + data::LoadResult output; + + // read full memory. TODO: only read part of memory + io::DiskMemory(std::filesystem::path(input.path), std::make_shared<io::NlohmannJSONDiskReader>()); + + output.success = true; + return output; + } + + // LTM STORING + data::StoreResult MemoryToIceAdapter::store(const armem::data::StoreInput& input) + { + ARMARX_CHECK_NOT_NULL(memory); + ARMARX_CHECK_NOT_NULL(diskMemory); + data::StoreResult output; + + // Write full memory. TODO: only write part of memory + //diskMemory->append(*memory, input.path, std::make_shared<io::NlohmannJSONDiskWriter>()); + io::DiskMemory(*memory, input.path, std::make_shared<io::NlohmannJSONDiskWriter>()); + + output.success = true; + return output; + } + } diff --git a/source/RobotAPI/libraries/armem/server/MemoryToIceAdapter.h b/source/RobotAPI/libraries/armem/server/MemoryToIceAdapter.h index c6c61c6a18af5b8855e9b97b05b5d79cb73d3a49..0bee460e6c8f0ed6be98ae64b392c6efd8871dc3 100644 --- a/source/RobotAPI/libraries/armem/server/MemoryToIceAdapter.h +++ b/source/RobotAPI/libraries/armem/server/MemoryToIceAdapter.h @@ -4,6 +4,7 @@ #include <RobotAPI/interface/armem/client/MemoryListenerInterface.h> #include "../core/Memory.h" +#include "../core/io/DiskMemory.h" namespace armarx::armem::server @@ -21,13 +22,12 @@ namespace armarx::armem::server public: /// Construct an MemoryToIceAdapter from an existing Memory. - MemoryToIceAdapter(Memory* memory = nullptr); + MemoryToIceAdapter(Memory* memory = nullptr, io::DiskMemory* diskMemory = nullptr); void setMemoryListener(client::MemoryListenerInterfacePrx memoryListener); // WRITING - data::AddSegmentResult addSegment( const data::AddSegmentInput& input, bool addCoreSegments = false); @@ -39,15 +39,19 @@ namespace armarx::armem::server data::CommitResult commit(const data::Commit& commitIce); armem::CommitResult commit(const armem::Commit& commit); - // READING - query::data::Result query(const armem::query::data::Input& input); + // LTM LOADING + data::LoadResult load(const armem::data::LoadInput& input); + + // LTM STORING + data::StoreResult store(const armem::data::StoreInput& input); public: Memory* memory; + io::DiskMemory* diskMemory; client::MemoryListenerInterfacePrx memoryListener; diff --git a/source/RobotAPI/libraries/armem/test/ArMemLTMTest.cpp b/source/RobotAPI/libraries/armem/test/ArMemLTMTest.cpp index dea566c5ee235868f23334f381095e1949f4f044..01754413bc733343d0677e43655edc3318b55c36 100644 --- a/source/RobotAPI/libraries/armem/test/ArMemLTMTest.cpp +++ b/source/RobotAPI/libraries/armem/test/ArMemLTMTest.cpp @@ -30,11 +30,14 @@ #include <RobotAPI/libraries/aron/core/navigator/data/AllNavigators.h> #include <RobotAPI/libraries/aron/core/navigator/type/AllNavigators.h> -#include <RobotAPI/libraries/armem/core/io/MemoryFileSystemStorage.h> #include <RobotAPI/libraries/aron/core/Randomizer.h> #include <RobotAPI/libraries/aron/core/Debug.h> +#include "../core/io/DiskMemory.h" + +#include "../core/io/diskWriter/NlohmannJSON/NlohmannJSONDiskWriter.h" + #include <filesystem> #include <iostream> @@ -46,15 +49,26 @@ namespace ArMemLTMTest { struct Fixture { - fs::path storagePath = "./TestMemoryExport"; + fs::path storagePath = "/tmp/TestMemoryExport"; Fixture() { clearStoragePath(); + assureStoragePath(); } ~Fixture() { - clearStoragePath(); + //clearStoragePath(); + } + + void assureStoragePath() + { + if (!fs::is_directory(storagePath)) + { + fs::create_directory(storagePath); + } + BOOST_TEST_INFO("Storage path: " << storagePath); + BOOST_REQUIRE(fs::exists(storagePath) && fs::is_directory(storagePath)); } void clearStoragePath() @@ -128,186 +142,73 @@ namespace ArMemLTMTest return t; } - }; -} -BOOST_FIXTURE_TEST_SUITE(ArMemLTMTest, Fixture) + template <class TypeNavigatorT> + void run(const std::string& memoryName, const std::string& memberNamePrefix) + { + aron::typenavigator::ObjectNavigatorPtr t = makeType<TypeNavigatorT>(memberNamePrefix); + armem::Memory memory = setupMemoryWithType(memoryName, t, nullptr, 15, 1); -/* -BOOST_AUTO_TEST_CASE(test_memory_export__easy_int_setup) -{ - std::string memoryName = "TestMemory_IntSetup"; + // create reader and writer + armem::io::DiskWriterPtr w = std::make_shared<armem::io::NlohmannJSONDiskWriter>(); + armem::io::DiskReaderPtr r = w->getCorrespondingDiskReader(); - aron::typenavigator::ObjectNavigatorPtr t = makeType<aron::typenavigator::AronIntTypeNavigator>("theInt"); - armem::Memory memory = setupMemoryWithType(memoryName, t, nullptr, 15, 1); + // export memory + BOOST_REQUIRE(fs::exists(storagePath)); + armem::io::DiskMemory dMem(memory, storagePath, w); + std::string mfs_str = dMem.toString(); - // export memory - BOOST_REQUIRE(!fs::exists(storagePath)); - armem::io::FileSystemMemoryManager mfs(storagePath, true); - mfs.writeOnDisk(memory); + armem::io::DiskMemory dMem2(storagePath, r); + std::string mfs2_str = dMem2.toString(); - std::string mfs_str = mfs.toString(); + //std::cout << "MFS1: " << std::endl; + //std::cout << mfs_str << std::endl; + //std::cout << "MFS2: " << std::endl; + //std::cout << mfs2_str << std::endl; + BOOST_CHECK_EQUAL(mfs_str == mfs2_str, true); - armem::io::FileSystemMemoryManager mfs2(storagePath); - mfs2.update(); + armem::Memory memory2 = dMem2.toMemory(); + memory2.name() = memoryName; - std::string mfs2_str = mfs2.toString(); + BOOST_CHECK_EQUAL(memory.equalsDeep(memory2), true); + } + }; +} - //std::cout << "MFS1: " << std::endl; - //std::cout << mfs_str << std::endl; - //std::cout << "MFS2: " << std::endl; - //std::cout << mfs2_str << std::endl; - BOOST_CHECK_EQUAL(mfs_str == mfs2_str, true); +BOOST_FIXTURE_TEST_SUITE(ArMemLTMTest, Fixture) - armem::Memory memory2 = mfs.readMemoryFromDisk(memoryName); - BOOST_CHECK_EQUAL(memory.equalsDeep(memory2), true); + +BOOST_AUTO_TEST_CASE(test_memory_export__easy_int_setup) +{ + run<aron::typenavigator::IntNavigator>("TestMemory_IntSetup", "theInt"); } BOOST_AUTO_TEST_CASE(test_memory_export__easy_long_setup) { - std::string memoryName = "TestMemory_LongSetup"; - - aron::typenavigator::ObjectNavigatorPtr t = makeType<aron::typenavigator::AronLongTypeNavigator>("theLong"); - armem::Memory memory = setupMemoryWithType(memoryName, t, nullptr, 15, 1); - - // export memory - BOOST_REQUIRE(!fs::exists(storagePath)); - armem::io::FileSystemMemoryManager mfs(storagePath, true); - mfs.writeOnDisk(memory); - - std::string mfs_str = mfs.toString(); - - armem::io::FileSystemMemoryManager mfs2(storagePath); - mfs2.update(); - - std::string mfs2_str = mfs2.toString(); - - //std::cout << "MFS1: " << std::endl; - //std::cout << mfs_str << std::endl; - //std::cout << "MFS2: " << std::endl; - //std::cout << mfs2_str << std::endl; - BOOST_CHECK_EQUAL(mfs_str == mfs2_str, true); - - armem::Memory memory2 = mfs.readMemoryFromDisk(memoryName); - BOOST_CHECK_EQUAL(memory.equalsDeep(memory2), true); + run<aron::typenavigator::LongNavigator>("TestMemory_LongSetup", "theLong"); } BOOST_AUTO_TEST_CASE(test_memory_export__easy_float_setup) { - std::string memoryName = "TestMemory_FloatSetup"; - - aron::typenavigator::ObjectNavigatorPtr t = makeType<aron::typenavigator::AronFloatTypeNavigator>("theFloat"); - armem::Memory memory = setupMemoryWithType(memoryName, t, nullptr, 15, 1); - - // export memory - BOOST_REQUIRE(!fs::exists(storagePath)); - armem::io::FileSystemMemoryManager mfs(storagePath, true); - mfs.writeOnDisk(memory); - - std::string mfs_str = mfs.toString(); - - armem::io::FileSystemMemoryManager mfs2(storagePath); - mfs2.update(); - - std::string mfs2_str = mfs2.toString(); - - //std::cout << "MFS1: " << std::endl; - //std::cout << mfs_str << std::endl; - //std::cout << "MFS2: " << std::endl; - //std::cout << mfs2_str << std::endl; - BOOST_CHECK_EQUAL(mfs_str == mfs2_str, true); - - armem::Memory memory2 = mfs.readMemoryFromDisk(memoryName); - BOOST_CHECK_EQUAL(memory.equalsDeep(memory2), true); + run<aron::typenavigator::FloatNavigator>("TestMemory_FloatSetup", "theFloat"); } BOOST_AUTO_TEST_CASE(test_memory_export__easy_double_setup) { - std::string memoryName = "TestMemory_DoubleSetup"; - - aron::typenavigator::ObjectNavigatorPtr t = makeType<aron::typenavigator::AronDoubleTypeNavigator>("theDouble"); - armem::Memory memory = setupMemoryWithType(memoryName, t, nullptr, 15, 1); - - // export memory - BOOST_REQUIRE(!fs::exists(storagePath)); - armem::io::FileSystemMemoryManager mfs(storagePath, true); - mfs.writeOnDisk(memory); - - std::string mfs_str = mfs.toString(); - - armem::io::FileSystemMemoryManager mfs2(storagePath); - mfs2.update(); - - std::string mfs2_str = mfs2.toString(); - - //std::cout << "MFS1: " << std::endl; - //std::cout << mfs_str << std::endl; - //std::cout << "MFS2: " << std::endl; - //std::cout << mfs2_str << std::endl; - BOOST_CHECK_EQUAL(mfs_str == mfs2_str, true); - - armem::Memory memory2 = mfs.readMemoryFromDisk(memoryName); - BOOST_CHECK_EQUAL(memory.equalsDeep(memory2), true); + run<aron::typenavigator::DoubleNavigator>("TestMemory_DoubleSetup", "theDouble"); } BOOST_AUTO_TEST_CASE(test_memory_export__easy_string_setup) { - std::string memoryName = "TestMemory_StringSetup"; - - aron::typenavigator::ObjectNavigatorPtr t = makeType<aron::typenavigator::AronStringTypeNavigator>("theString"); - armem::Memory memory = setupMemoryWithType(memoryName, t, nullptr, 15, 1); - - // export memory - BOOST_REQUIRE(!fs::exists(storagePath)); - armem::io::FileSystemMemoryManager mfs(storagePath, true); - mfs.writeOnDisk(memory); - - std::string mfs_str = mfs.toString(); - - armem::io::FileSystemMemoryManager mfs2(storagePath); - mfs2.update(); - - std::string mfs2_str = mfs2.toString(); - - //std::cout << "MFS1: " << std::endl; - //std::cout << mfs_str << std::endl; - //std::cout << "MFS2: " << std::endl; - //std::cout << mfs2_str << std::endl; - BOOST_CHECK_EQUAL(mfs_str == mfs2_str, true); - - armem::Memory memory2 = mfs.readMemoryFromDisk(memoryName); - BOOST_CHECK_EQUAL(memory.equalsDeep(memory2), true); + run<aron::typenavigator::StringNavigator>("TestMemory_StringSetup", "theString"); } BOOST_AUTO_TEST_CASE(test_memory_export__easy_bool_setup) { - std::string memoryName = "TestMemory_BoolSetup"; - - aron::typenavigator::ObjectNavigatorPtr t = makeType<aron::typenavigator::AronBoolTypeNavigator>("theBool"); - armem::Memory memory = setupMemoryWithType(memoryName, t, nullptr, 15, 1); - - // export memory - BOOST_REQUIRE(!fs::exists(storagePath)); - armem::io::FileSystemMemoryManager mfs(storagePath, true); - mfs.writeOnDisk(memory); - - std::string mfs_str = mfs.toString(); - - armem::io::FileSystemMemoryManager mfs2(storagePath); - mfs2.update(); - - std::string mfs2_str = mfs2.toString(); - - //std::cout << "MFS1: " << std::endl; - //std::cout << mfs_str << std::endl; - //std::cout << "MFS2: " << std::endl; - //std::cout << mfs2_str << std::endl; - BOOST_CHECK_EQUAL(mfs_str == mfs2_str, true); - - armem::Memory memory2 = mfs.readMemoryFromDisk(memoryName); - BOOST_CHECK_EQUAL(memory.equalsDeep(memory2), true); + run<aron::typenavigator::BoolNavigator>("TestMemory_BoolSetup", "theBool"); } +/* BOOST_AUTO_TEST_CASE(test_memory_export__easy_rainer_setup) { std::string memoryName = "TestMemory_RainerSetup"; @@ -316,17 +217,17 @@ BOOST_AUTO_TEST_CASE(test_memory_export__easy_rainer_setup) t->setObjectName("TestRainerType1"); aron::typenavigator::DictNavigatorPtr tm1(new aron::typenavigator::DictNavigator(aron::Path())); - aron::typenavigator::AronFloatTypeNavigatorPtr tm1m1(new aron::typenavigator::AronFloatTypeNavigator(aron::Path())); + aron::typenavigator::FloatNavigatorPtr tm1m1(new aron::typenavigator::FloatNavigator(aron::Path())); tm1->setAcceptedType(tm1m1); - aron::typenavigator::AronStringTypeNavigatorPtr tm2(new aron::typenavigator::AronStringTypeNavigator(aron::Path())); + aron::typenavigator::StringNavigatorPtr tm2(new aron::typenavigator::StringNavigator(aron::Path())); aron::typenavigator::DictNavigatorPtr tm3(new aron::typenavigator::DictNavigator(aron::Path())); - aron::typenavigator::AronStringTypeNavigatorPtr tm3m1(new aron::typenavigator::AronStringTypeNavigator(aron::Path())); + aron::typenavigator::StringNavigatorPtr tm3m1(new aron::typenavigator::StringNavigator(aron::Path())); tm3->setAcceptedType(tm3m1); - aron::typenavigator::AronStringTypeNavigatorPtr tm4(new aron::typenavigator::AronStringTypeNavigator(aron::Path())); - t->addAcceptedType("float_params", tm1); - t->addAcceptedType("name", tm2); - //t->addAcceptedType("string_params", tm3); - t->addAcceptedType("type", tm4); + aron::typenavigator::StringNavigatorPtr tm4(new aron::typenavigator::StringNavigator(aron::Path())); + t->addMemberType("float_params", tm1); + t->addMemberType("name", tm2); + //t->addMemberType("string_params", tm3); + t->addMemberType("type", tm4); armem::Memory memory = setupMemoryWithType(memoryName, t, nullptr, 15, 1); diff --git a/source/RobotAPI/libraries/armem_gui/CMakeLists.txt b/source/RobotAPI/libraries/armem_gui/CMakeLists.txt index 4b49856774ca0fd7236ad259b2b2346094c0501b..c0a27825ee0ee7aae1770e3a426054194bdfd8ef 100644 --- a/source/RobotAPI/libraries/armem_gui/CMakeLists.txt +++ b/source/RobotAPI/libraries/armem_gui/CMakeLists.txt @@ -17,6 +17,7 @@ set(SOURCES MemoryViewer.cpp PeriodicUpdateWidget.cpp + LTMControlWidget.cpp gui_utils.cpp lifecycle.cpp @@ -38,6 +39,7 @@ set(HEADERS MemoryViewer.h PeriodicUpdateWidget.h + LTMControlWidget.h TreeWidgetBuilder.h gui_utils.h lifecycle.h diff --git a/source/RobotAPI/libraries/armem_gui/LTMControlWidget.cpp b/source/RobotAPI/libraries/armem_gui/LTMControlWidget.cpp new file mode 100644 index 0000000000000000000000000000000000000000..41a66032b56eea72f312c1f1cff157a6ef48c66c --- /dev/null +++ b/source/RobotAPI/libraries/armem_gui/LTMControlWidget.cpp @@ -0,0 +1,69 @@ +#include "LTMControlWidget.h" + +#include <QPushButton> +#include <QLineEdit> +#include <QTimer> +#include <QHBoxLayout> + +#include <cmath> + + +namespace armarx::armem::gui +{ + + LTMControlWidget::LTMControlWidget() + { + setSizePolicy(QSizePolicy::Policy::Minimum, QSizePolicy::Policy::Fixed); + + QLayout* layout = new QHBoxLayout(); + this->setLayout(layout); + + const int margin = 0; + layout->setContentsMargins(margin, margin, margin, margin); + + _lineEdit = new QLineEdit("/tmp/MemoryExport", this); + _mkdirButton = new QPushButton("mkdir", this); + _storeButton = new QPushButton("store", this); + _loadButton = new QPushButton("load", this); + + + layout->addWidget(_lineEdit); + layout->addWidget(_mkdirButton); + layout->addWidget(_storeButton); + layout->addWidget(_loadButton); + + // Private connections. + + // Public connections. + connect(_mkdirButton, &QPushButton::pressed, this, &This::mkdir); + connect(_loadButton, &QPushButton::pressed, this, &This::load); + connect(_storeButton, &QPushButton::pressed, this, &This::store); + } + + QLineEdit* LTMControlWidget::pathInputBox() + { + return _lineEdit; + } + + QString LTMControlWidget::getEnteredPath() + { + return _lineEdit->text(); + } + + QPushButton* LTMControlWidget::loadButton() + { + return _loadButton; + } + + QPushButton* LTMControlWidget::storeButton() + { + return _storeButton; + } + + QPushButton* LTMControlWidget::mkdirButton() + { + return _mkdirButton; + } + +} + diff --git a/source/RobotAPI/libraries/armem_gui/LTMControlWidget.h b/source/RobotAPI/libraries/armem_gui/LTMControlWidget.h new file mode 100644 index 0000000000000000000000000000000000000000..f65cabe02aa75b3c75e17a3cc2ec7117fb55266c --- /dev/null +++ b/source/RobotAPI/libraries/armem_gui/LTMControlWidget.h @@ -0,0 +1,52 @@ +#pragma once + +#include <QWidget> + +class QPushButton; +class QLineEdit; + +namespace armarx::armem::gui +{ + + class LTMControlWidget : public QWidget + { + Q_OBJECT + using This = LTMControlWidget; + + public: + + LTMControlWidget(); + + QLineEdit* pathInputBox(); + QString getEnteredPath(); + + QPushButton* mkdirButton(); + QPushButton* loadButton(); + QPushButton* storeButton(); + + public slots: + + signals: + + void load(); + void store(); + + void mkdir(); + + private slots: + + + signals: + + + + private: + + QLineEdit* _lineEdit; + QPushButton* _mkdirButton; + QPushButton* _loadButton; + QPushButton* _storeButton; + + }; + +} diff --git a/source/RobotAPI/libraries/armem_gui/MemoryViewer.cpp b/source/RobotAPI/libraries/armem_gui/MemoryViewer.cpp index 2cff7aa28476ba530a8b72febb11d563e5101b0b..27639cf008058b6c57c3eb3f289729c368707a74 100644 --- a/source/RobotAPI/libraries/armem_gui/MemoryViewer.cpp +++ b/source/RobotAPI/libraries/armem_gui/MemoryViewer.cpp @@ -3,6 +3,8 @@ #include <RobotAPI/libraries/armem/core/ice_conversions.h> #include <RobotAPI/libraries/armem_gui/gui_utils.h> +#include <RobotAPI/libraries/armem/core/io/diskWriter/NlohmannJSON/NlohmannJSONDiskWriter.h> + #include <ArmarXGui/libraries/SimpleConfigDialog/SimpleConfigDialog.h> #include <ArmarXCore/core/ManagedIceObject.h> @@ -17,11 +19,14 @@ #include <QLayout> #include <QSettings> +#include <filesystem> + namespace armarx::armem::gui { MemoryViewer::MemoryViewer( + QBoxLayout* ltmControlWidgetLayout, QBoxLayout* updateWidgetLayout, QGroupBox* _memoryGroupBox, QLayout* memoryGroupBoxParentLayout, QGroupBox* _instanceGroupBox, QLayout* instanceGroupBoxParentLayout, @@ -32,6 +37,11 @@ namespace armarx::armem::gui this->statusLabel = statusLabel; this->statusLabel->clear(); + // LTM Control + this->ltmControlWidgetLayout = ltmControlWidgetLayout; + ltmControlWidget = new armem::gui::LTMControlWidget(); + ltmControlWidgetLayout->insertWidget(0, ltmControlWidget); + // Update timer this->updateWidgetLayout = updateWidgetLayout; updateWidget = new armem::gui::PeriodicUpdateWidget(2.0, 60); @@ -46,8 +56,12 @@ namespace armarx::armem::gui this->instanceGroup->setStatusLabel(statusLabel); ARMARX_CHECK_NULL(_instanceGroupBox); - connect(this, &This::connected, this, &This::updateMemory); + + connect(ltmControlWidget, &armem::gui::LTMControlWidget::store, this, &This::store); + connect(ltmControlWidget, &armem::gui::LTMControlWidget::load, this, &This::load); + connect(ltmControlWidget, &armem::gui::LTMControlWidget::mkdir, this, &This::mkdir); + connect(updateWidget, &armem::gui::PeriodicUpdateWidget::update, this, &This::updateMemory); connect(this, &This::memoryDataChanged, this, &This::updateMemoryTree); @@ -100,6 +114,79 @@ namespace armarx::armem::gui emit disconnected(); } + void MemoryViewer::store() + { + if (!memoryReader) + { + return; + } + + TIMING_START(MemoryDump); + QString qs = ltmControlWidget->getEnteredPath(); + std::string utf8_text = qs.toUtf8().constData(); + + if (this->memoryData) + { + io::DiskMemory d(*this->memoryData, utf8_text, std::make_shared<io::NlohmannJSONDiskWriter>()); + } + + TIMING_END_STREAM(MemoryDump, ARMARX_VERBOSE); + + if (statusLabel) + { + statusLabel->setText(QString::fromStdString("Successfully stored memory.")); + } + } + + void MemoryViewer::load() + { + TIMING_START(MemoryLoad); + QString qs = ltmControlWidget->getEnteredPath(); + std::string utf8_text = qs.toUtf8().constData(); + + io::DiskMemory d(std::filesystem::path(utf8_text), std::make_shared<io::NlohmannJSONDiskReader>()); + this->memoryData = d.toMemory(); + + TIMING_END_STREAM(MemoryLoad, ARMARX_VERBOSE); + + if (this->memoryData) + { + emit memoryDataChanged(); + } + } + + void MemoryViewer::mkdir() + { + QString qs = ltmControlWidget->getEnteredPath(); + std::string utf8_text = qs.toUtf8().constData(); + std::filesystem::path p(utf8_text); + + if (!std::filesystem::exists(p)) + { + if (!std::filesystem::exists(p.parent_path())) + { + if (statusLabel) + { + statusLabel->setText(QString::fromStdString("Could not create Folder. At least parent must exist.")); + } + } + else + { + std::filesystem::create_directory(p); + if (statusLabel) + { + statusLabel->setText(QString::fromStdString("Successfully created folder '" + p.string() + "'.")); + } + } + } + else + { + if (statusLabel) + { + statusLabel->setText(QString::fromStdString("Folder already exists.")); + } + } + } void MemoryViewer::updateMemory() { diff --git a/source/RobotAPI/libraries/armem_gui/MemoryViewer.h b/source/RobotAPI/libraries/armem_gui/MemoryViewer.h index df66ad86fa603443119744d0ee152f5f126e805a..a1b171b599b2f1eb7aac54cc874319ed6133e066 100644 --- a/source/RobotAPI/libraries/armem_gui/MemoryViewer.h +++ b/source/RobotAPI/libraries/armem_gui/MemoryViewer.h @@ -13,7 +13,7 @@ #include <RobotAPI/libraries/armem_gui/instance/GroupBox.h> #include <RobotAPI/libraries/armem_gui/memory/GroupBox.h> #include <RobotAPI/libraries/armem_gui/PeriodicUpdateWidget.h> - +#include <RobotAPI/libraries/armem_gui/LTMControlWidget.h> class QBoxLayout; @@ -45,6 +45,7 @@ namespace armarx::armem::gui public: MemoryViewer( + QBoxLayout* ltmControlWidgetLayout, QBoxLayout* updateWidgetLayout, QGroupBox* _memoryGroupBox, QLayout* memoryGroupBoxParentLayout, QGroupBox* _instanceGroupBox, QLayout* instanceGroupBoxParentLayout, @@ -63,6 +64,10 @@ namespace armarx::armem::gui public slots: + void store(); + void load(); + void mkdir(); + void updateMemory(); void updateInstanceTree(const armem::MemoryID& selectedID); @@ -101,6 +106,8 @@ namespace armarx::armem::gui std::optional<armem::Memory> memoryData; + QLayout* ltmControlWidgetLayout; + armem::gui::LTMControlWidget* ltmControlWidget; QLayout* updateWidgetLayout; armem::gui::PeriodicUpdateWidget* updateWidget; diff --git a/source/RobotAPI/libraries/aron/core/CMakeLists.txt b/source/RobotAPI/libraries/aron/core/CMakeLists.txt index 0bdb8203c8083108012fb02e10eac9b7b7a2779e..3e43781ec6ae4cff3ff33ded8965deec84cd833c 100644 --- a/source/RobotAPI/libraries/aron/core/CMakeLists.txt +++ b/source/RobotAPI/libraries/aron/core/CMakeLists.txt @@ -21,7 +21,8 @@ set(LIBS ArmarXCore RobotAPIInterfaces cppgen - ${Simox_LIBS} + + SimoxUtility ) set(LIB_FILES diff --git a/source/RobotAPI/libraries/aron/core/Debug.h b/source/RobotAPI/libraries/aron/core/Debug.h index 6687e8909ffb6d33918cde779f3e9d7f8a342007..28b3958646b984914a6092d272d5b39d3a7dd2ba 100644 --- a/source/RobotAPI/libraries/aron/core/Debug.h +++ b/source/RobotAPI/libraries/aron/core/Debug.h @@ -47,7 +47,7 @@ namespace armarx::aron static std::string AronDataPtrToString(const data::AronDataPtr& data) { dataIO::writer::NlohmannJSONWriter w; - dataIO::Visitor::SetupWriterFromAronDataPtr(w, data); + dataIO::Visitor::VisitAndSetup(w, data); return w.getResult().dump(2); } @@ -58,14 +58,14 @@ namespace armarx::aron return ""; } dataIO::writer::NlohmannJSONWriter w; - dataIO::Visitor::SetupWriterFromAronDataPtr(w, data); + dataIO::Visitor::VisitAndSetup(w, data); return w.getResult().dump(2); } static std::string AronTypePtrToString(const type::AronTypePtr& data) { typeIO::writer::NlohmannJSONWriter w; - typeIO::Visitor::SetupWriterFromAronTypePtr(w, data); + typeIO::Visitor::VisitAndSetup(w, data); return w.getResult().dump(2); } @@ -76,7 +76,7 @@ namespace armarx::aron return ""; } typeIO::writer::NlohmannJSONWriter w; - typeIO::Visitor::SetupWriterFromAronTypePtr(w, data); + typeIO::Visitor::VisitAndSetup(w, data); return w.getResult().dump(2); } }; diff --git a/source/RobotAPI/libraries/aron/core/Descriptor.h b/source/RobotAPI/libraries/aron/core/Descriptor.h index 8beadd6fe75e32997382623f96e68f7a5ee70f47..26e9e24ba442a6d04f7590181e8736ace884ab29 100644 --- a/source/RobotAPI/libraries/aron/core/Descriptor.h +++ b/source/RobotAPI/libraries/aron/core/Descriptor.h @@ -35,7 +35,7 @@ namespace armarx::aron::type { - enum Descriptor + enum class Descriptor { #define RUN_ARON_MACRO(upperType, lowerType, capsType) \ e##upperType, @@ -48,11 +48,11 @@ namespace armarx::aron::type const std::map<type::Descriptor, std::string> _descriptorstring = { #define RUN_ARON_MACRO(upperType, lowerType, capsType) \ - { e##upperType, "armarx::aron::type::Descriptor::e" + std::string(#upperType) }, + { Descriptor::e##upperType, "armarx::aron::type::Descriptor::e" + std::string(#upperType) }, HANDLE_ALL_ARON_TYPES #undef RUN_ARON_MACRO - {eUnknown, "armarx::aron::type::Descriptor::eUnknown"} + {Descriptor::eUnknown, "armarx::aron::type::Descriptor::eUnknown"} }; inline std::string DESCRIPTOR_TO_STRING(const type::Descriptor d) @@ -63,7 +63,7 @@ namespace armarx::aron::type namespace armarx::aron::data { - enum Descriptor + enum class Descriptor { #define RUN_ARON_MACRO(upperType, lowerType, capsType) \ e##upperType, @@ -76,11 +76,11 @@ namespace armarx::aron::data const std::map<data::Descriptor, std::string> _descriptorstring = { #define RUN_ARON_MACRO(upperType, lowerType, capsType) \ - { e##upperType, "armarx::aron::data::Descriptor::e" + std::string(#upperType) }, + { Descriptor::e##upperType, "armarx::aron::data::Descriptor::e" + std::string(#upperType) }, HANDLE_ALL_ARON_DATA #undef RUN_ARON_MACRO - {eUnknown, "armarx::aron::data::Descriptor::eUnknown"} + {Descriptor::eUnknown, "armarx::aron::data::Descriptor::eUnknown"} }; inline std::string DESCRIPTOR_TO_STRING(const data::Descriptor d) diff --git a/source/RobotAPI/libraries/aron/core/Randomizer.h b/source/RobotAPI/libraries/aron/core/Randomizer.h index aeefb6913607dde05b926bfc237262a490fa93a4..315dbed6511f2933fda4dff223a87c6f473b0592 100644 --- a/source/RobotAPI/libraries/aron/core/Randomizer.h +++ b/source/RobotAPI/libraries/aron/core/Randomizer.h @@ -44,13 +44,13 @@ namespace armarx::aron typenavigator::NavigatorPtr generateRandomType(bool mustBeObject = false) const { - type::Descriptor nextType = type::eObject; + type::Descriptor nextType = type::Descriptor::eObject; if (!mustBeObject) { std::vector<type::Descriptor> descriptors = { #define RUN_ARON_MACRO(upperType, lowerType, capsType) \ - type::e##upperType, + type::Descriptor::e##upperType, HANDLE_ALL_ARON_TYPES #undef RUN_ARON_MACRO @@ -62,7 +62,7 @@ namespace armarx::aron switch (nextType) { - case type::eObject: + case type::Descriptor::eObject: { typenavigator::ObjectNavigatorPtr t = typenavigator::ObjectNavigatorPtr(new typenavigator::ObjectNavigator(Path())); std::string objectName = generateRandomWord(); @@ -81,7 +81,7 @@ namespace armarx::aron } return t; } - case type::eDict: + case type::Descriptor::eDict: { typenavigator::DictNavigatorPtr t = typenavigator::DictNavigatorPtr(new typenavigator::DictNavigator()); typenavigator::NavigatorPtr a = generateRandomType(false); @@ -89,7 +89,7 @@ namespace armarx::aron t->setAcceptedType(a); return t; } - case type::eTuple: + case type::Descriptor::eTuple: { typenavigator::TupleNavigatorPtr t = typenavigator::TupleNavigatorPtr(new typenavigator::TupleNavigator()); @@ -101,7 +101,7 @@ namespace armarx::aron } return t; } - case type::eList: + case type::Descriptor::eList: { typenavigator::ListNavigatorPtr t = typenavigator::ListNavigatorPtr(new typenavigator::ListNavigator()); typenavigator::NavigatorPtr a = generateRandomType(false); @@ -109,7 +109,7 @@ namespace armarx::aron t->setAcceptedType(a); return t; } - case type::ePair: + case type::Descriptor::ePair: { typenavigator::PairNavigatorPtr t = typenavigator::PairNavigatorPtr(new typenavigator::PairNavigator()); typenavigator::NavigatorPtr a = generateRandomType(false); @@ -119,46 +119,46 @@ namespace armarx::aron t->setSecondAcceptedType(b); return t; } - case type::eEigenMatrix: - case type::eEigenQuaternion: - case type::eIVTCByteImage: - case type::eOpenCVMat: - case type::ePCLPointCloud: - case type::ePosition: - case type::eOrientation: - case type::ePose: - - case type::eInt: + case type::Descriptor::eEigenMatrix: + case type::Descriptor::eEigenQuaternion: + case type::Descriptor::eIVTCByteImage: + case type::Descriptor::eOpenCVMat: + case type::Descriptor::ePCLPointCloud: + case type::Descriptor::ePosition: + case type::Descriptor::eOrientation: + case type::Descriptor::ePose: + + case type::Descriptor::eInt: { auto t = std::make_shared<typenavigator::IntNavigator>(); return t; } - case type::eLong: + case type::Descriptor::eLong: { auto t = std::make_shared<typenavigator::LongNavigator>(); return t; } - case type::eFloat: + case type::Descriptor::eFloat: { auto t = std::make_shared<typenavigator::FloatNavigator>(); return t; } - case type::eDouble: + case type::Descriptor::eDouble: { auto t = std::make_shared<typenavigator::DoubleNavigator>(); return t; } - case type::eString: + case type::Descriptor::eString: { auto t = std::make_shared<typenavigator::StringNavigator>(); return t; } - case type::eBool: + case type::Descriptor::eBool: { auto t = std::make_shared<typenavigator::BoolNavigator>(); return t; } - case type::eTime: + case type::Descriptor::eTime: { auto t = std::make_shared<typenavigator::TimeNavigator>(); return t; @@ -176,7 +176,7 @@ namespace armarx::aron switch (desc) { // In an object, we do not want to edit the keys. - case type::eObject: + case type::Descriptor::eObject: { typenavigator::ObjectNavigatorPtr t = typenavigator::ObjectNavigator::DynamicCastAndCheck(type); datanavigator::DictNavigatorPtr d = datanavigator::DictNavigatorPtr(new datanavigator::DictNavigator()); @@ -188,14 +188,14 @@ namespace armarx::aron } // here all totally random - case type::eDict: + case type::Descriptor::eDict: { typenavigator::DictNavigatorPtr t = typenavigator::DictNavigator::DynamicCastAndCheck(type); return datanavigator::NavigatorPtr(new datanavigator::DictNavigator()); } #define RUN_ARON_MACRO(upperType, lowerType, capsType) \ -case type::e##upperType: \ +case type::Descriptor::e##upperType: \ { \ typenavigator::upperType##NavigatorPtr t = typenavigator::upperType##Navigator::DynamicCastAndCheck(type); \ return datanavigator::NavigatorPtr(new datanavigator::ListNavigator()); \ @@ -205,7 +205,7 @@ case type::e##upperType: \ #undef RUN_ARON_MACRO #define RUN_ARON_MACRO(upperType, lowerType, capsType) \ -case type::e##upperType: \ +case type::Descriptor::e##upperType: \ { \ typenavigator::upperType##NavigatorPtr t = typenavigator::upperType##Navigator::DynamicCastAndCheck(type); \ datanavigator::NDArrayNavigatorPtr ndarray = datanavigator::NDArrayNavigatorPtr(new datanavigator::NDArrayNavigator()); \ @@ -216,7 +216,7 @@ case type::e##upperType: \ #undef RUN_ARON_MACRO #define RUN_ARON_MACRO(upperType, lowerType, capsType, upperData, lowerData, capsData) \ -case type::e##upperType: \ +case type::Descriptor::e##upperType: \ { \ typenavigator::upperType##NavigatorPtr t = typenavigator::upperType##Navigator::DynamicCastAndCheck(type); \ return datanavigator::NavigatorPtr(new datanavigator::upperData##Navigator()); \ @@ -239,7 +239,7 @@ case type::e##upperType: \ { #define RUN_ARON_MACRO(upperType, lowerType, capsType, upperData, lowerData, capsData) \ -case type::e##upperType: \ +case type::Descriptor::e##upperType: \ { \ typenavigator::upperType##NavigatorPtr t = typenavigator::upperType##Navigator::DynamicCastAndCheck(type); \ datanavigator::upperData##NavigatorPtr d = datanavigator::upperData##Navigator::DynamicCastAndCheck(data); \ diff --git a/source/RobotAPI/libraries/aron/core/codegenerator/codeWriter/cpp/serializer/SerializerFactory.cpp b/source/RobotAPI/libraries/aron/core/codegenerator/codeWriter/cpp/serializer/SerializerFactory.cpp index 7b777b8201d2ddfa302135a1b7795afd134a8c9d..15d698675592fa368cca5b212300d839c2142b8f 100644 --- a/source/RobotAPI/libraries/aron/core/codegenerator/codeWriter/cpp/serializer/SerializerFactory.cpp +++ b/source/RobotAPI/libraries/aron/core/codegenerator/codeWriter/cpp/serializer/SerializerFactory.cpp @@ -36,27 +36,27 @@ namespace armarx::aron::cppcodegenerator { static const std::map<type::Descriptor, SerializerFactoryPtr> Factories = { - {type::eObject, SerializerFactoryPtr(new ObjectSerializerFactory())}, - {type::eDict, SerializerFactoryPtr(new DictSerializerFactory())}, - {type::eList, SerializerFactoryPtr(new ListSerializerFactory())}, - {type::eTuple, SerializerFactoryPtr(new TupleSerializerFactory())}, - {type::ePair, SerializerFactoryPtr(new PairSerializerFactory())}, - {type::eEigenMatrix, SerializerFactoryPtr(new EigenMatrixSerializerFactory())}, - {type::eEigenQuaternion, SerializerFactoryPtr(new EigenQuaternionSerializerFactory())}, - {type::eIVTCByteImage, SerializerFactoryPtr(new IVTCByteImageSerializerFactory())}, - {type::eOpenCVMat, SerializerFactoryPtr(new OpenCVMatSerializerFactory())}, - {type::ePCLPointCloud, SerializerFactoryPtr(new PCLPointCloudSerializerFactory())}, - {type::ePosition, SerializerFactoryPtr(new PositionSerializerFactory())}, - {type::eOrientation, SerializerFactoryPtr(new OrientationSerializerFactory())}, - {type::ePose, SerializerFactoryPtr(new PoseSerializerFactory())}, - {type::eIntEnum, SerializerFactoryPtr(new IntEnumSerializerFactory())}, - {type::eInt, SerializerFactoryPtr(new IntSerializerFactory())}, - {type::eLong, SerializerFactoryPtr(new LongSerializerFactory())}, - {type::eFloat, SerializerFactoryPtr(new FloatSerializerFactory())}, - {type::eDouble, SerializerFactoryPtr(new DoubleSerializerFactory())}, - {type::eString, SerializerFactoryPtr(new StringSerializerFactory())}, - {type::eBool, SerializerFactoryPtr(new BoolSerializerFactory())}, - {type::eTime, SerializerFactoryPtr(new TimeSerializerFactory())} + {type::Descriptor::eObject, SerializerFactoryPtr(new ObjectSerializerFactory())}, + {type::Descriptor::eDict, SerializerFactoryPtr(new DictSerializerFactory())}, + {type::Descriptor::eList, SerializerFactoryPtr(new ListSerializerFactory())}, + {type::Descriptor::eTuple, SerializerFactoryPtr(new TupleSerializerFactory())}, + {type::Descriptor::ePair, SerializerFactoryPtr(new PairSerializerFactory())}, + {type::Descriptor::eEigenMatrix, SerializerFactoryPtr(new EigenMatrixSerializerFactory())}, + {type::Descriptor::eEigenQuaternion, SerializerFactoryPtr(new EigenQuaternionSerializerFactory())}, + {type::Descriptor::eIVTCByteImage, SerializerFactoryPtr(new IVTCByteImageSerializerFactory())}, + {type::Descriptor::eOpenCVMat, SerializerFactoryPtr(new OpenCVMatSerializerFactory())}, + {type::Descriptor::ePCLPointCloud, SerializerFactoryPtr(new PCLPointCloudSerializerFactory())}, + {type::Descriptor::ePosition, SerializerFactoryPtr(new PositionSerializerFactory())}, + {type::Descriptor::eOrientation, SerializerFactoryPtr(new OrientationSerializerFactory())}, + {type::Descriptor::ePose, SerializerFactoryPtr(new PoseSerializerFactory())}, + {type::Descriptor::eIntEnum, SerializerFactoryPtr(new IntEnumSerializerFactory())}, + {type::Descriptor::eInt, SerializerFactoryPtr(new IntSerializerFactory())}, + {type::Descriptor::eLong, SerializerFactoryPtr(new LongSerializerFactory())}, + {type::Descriptor::eFloat, SerializerFactoryPtr(new FloatSerializerFactory())}, + {type::Descriptor::eDouble, SerializerFactoryPtr(new DoubleSerializerFactory())}, + {type::Descriptor::eString, SerializerFactoryPtr(new StringSerializerFactory())}, + {type::Descriptor::eBool, SerializerFactoryPtr(new BoolSerializerFactory())}, + {type::Descriptor::eTime, SerializerFactoryPtr(new TimeSerializerFactory())} }; //CheckIfPtrIsNull("NavigatorFactory", "create", path, n); diff --git a/source/RobotAPI/libraries/aron/core/codegenerator/codeWriter/cpp/serializer/toplevel/IntEnumClass.h b/source/RobotAPI/libraries/aron/core/codegenerator/codeWriter/cpp/serializer/toplevel/IntEnumClass.h index 5e7d3875fe29a4f10e15fb7123fecf33276e19d1..cf5b46c25b102ce0d2e49d4e971a6c5935f50000 100644 --- a/source/RobotAPI/libraries/aron/core/codegenerator/codeWriter/cpp/serializer/toplevel/IntEnumClass.h +++ b/source/RobotAPI/libraries/aron/core/codegenerator/codeWriter/cpp/serializer/toplevel/IntEnumClass.h @@ -61,6 +61,7 @@ namespace armarx::aron::cppcodegenerator::serializer virtual CppBlockPtr getReadBlock(const std::string&) const override; virtual CppBlockPtr getEqualsBlock(const std::string&, const std::string&) const override; + // TODO: Move some of those methods to upper class for enums (if we want to support multiple enums) CppCtorPtr toCopyCtor(const std::string&) const; CppCtorPtr toInnerEnumCtor(const std::string&) const; CppEnumPtr toInnerEnumDefinition() const; diff --git a/source/RobotAPI/libraries/aron/core/io/Data.h b/source/RobotAPI/libraries/aron/core/io/Data.h index 6d29388942067854205998b2c0aaef4e4b74a402..73c693b53311f47232c1b581698dc7765495c8c4 100644 --- a/source/RobotAPI/libraries/aron/core/io/Data.h +++ b/source/RobotAPI/libraries/aron/core/io/Data.h @@ -40,18 +40,18 @@ namespace armarx::aron::io public: // TODO: Remove copy from ReaderWriter - static constexpr const char* READER_WRITER_NAME_SLUG = "ARON_NAME"; - static constexpr const char* READER_WRITER_DICT_ACCEPTED_TYPE_SLUG = "ARON_DICT_ACCEPTED_TYPE"; - static constexpr const char* READER_WRITER_LIST_ACCEPTED_TYPE_SLUG = "ARON_LIST_ACCEPTED_TYPE"; - - static constexpr const char* READER_WRITER_NDARRAY_NAME_SLUG = "ARON_NDARRAY_NAME"; - static constexpr const char* READER_WRITER_NDARRAY_DIMENSIONS_SLUG = "ARON_NDARRAY_DIMESIONS"; - static constexpr const char* READER_WRITER_NDARRAY_TYPE_SLUG = "ARON_NDARRAY_TYPE"; - static constexpr const char* READER_WRITER_NDARRAY_DATA_SLUG = "ARON_NDARRAY_DATA"; - - static constexpr const char* READER_WRITER_INT_ENUM_NAME_SLUG = "ARON_INT_ENUM_NAME"; - static constexpr const char* READER_WRITER_INT_ENUM_VALUE_SLUG = "ARON_INT_ENUM_VALUE"; - static constexpr const char* READER_WRITER_ENUM_KEY_SLUG = "ARON_ENUM_KEY"; + static constexpr const char* READER_WRITER_NAME_SLUG = "__ARON_NAME"; + static constexpr const char* READER_WRITER_DICT_ACCEPTED_TYPE_SLUG = "__ARON_DICT_ACCEPTED_TYPE"; + static constexpr const char* READER_WRITER_LIST_ACCEPTED_TYPE_SLUG = "__ARON_LIST_ACCEPTED_TYPE"; + + static constexpr const char* READER_WRITER_NDARRAY_NAME_SLUG = "__ARON_NDARRAY_NAME"; + static constexpr const char* READER_WRITER_NDARRAY_DIMENSIONS_SLUG = "__ARON_NDARRAY_DIMESIONS"; + static constexpr const char* READER_WRITER_NDARRAY_TYPE_SLUG = "__ARON_NDARRAY_TYPE"; + static constexpr const char* READER_WRITER_NDARRAY_DATA_SLUG = "__ARON_NDARRAY_DATA"; + + static constexpr const char* READER_WRITER_INT_ENUM_NAME_SLUG = "__ARON_INT_ENUM_NAME"; + static constexpr const char* READER_WRITER_INT_ENUM_VALUE_SLUG = "__ARON_INT_ENUM_VALUE"; + static constexpr const char* READER_WRITER_ENUM_KEY_SLUG = "__ARON_ENUM_KEY"; #define RUN_ARON_MACRO(upperType, lowerType, capsType) \ static constexpr const char* READER_WRITER_##capsType##_TYPENAME_SLUG = #capsType; diff --git a/source/RobotAPI/libraries/aron/core/io/dataIO/Reader.h b/source/RobotAPI/libraries/aron/core/io/dataIO/Reader.h index 7df44a015c8f93f531e1e54c8dd2524ae98308d6..574b9167d3f6b77e4b2a8434a5dfb90911cabd2c 100644 --- a/source/RobotAPI/libraries/aron/core/io/dataIO/Reader.h +++ b/source/RobotAPI/libraries/aron/core/io/dataIO/Reader.h @@ -64,6 +64,6 @@ namespace armarx::aron::dataIO virtual void loadMember(const std::string&) = 0; // Helper functions - virtual data::Descriptor getTypeOfNext(const type::Descriptor hint = type::eUnknown) const = 0; + virtual data::Descriptor getTypeOfNext(const type::Descriptor hint = type::Descriptor::eUnknown) const = 0; }; } diff --git a/source/RobotAPI/libraries/aron/core/io/dataIO/converter/Converter.cpp b/source/RobotAPI/libraries/aron/core/io/dataIO/converter/Converter.cpp index 13b6703cd69bffe9e6c8f89cf4164ada98649bc0..a0feee781f33f1623d24948600a26370368db685 100644 --- a/source/RobotAPI/libraries/aron/core/io/dataIO/converter/Converter.cpp +++ b/source/RobotAPI/libraries/aron/core/io/dataIO/converter/Converter.cpp @@ -31,21 +31,22 @@ namespace armarx::aron::dataIO { - void Converter::ConvertFromReader(ReaderInterface& reader, WriterInterface& writer, const aron::typenavigator::NavigatorPtr& expectedStructure) + void Converter::ReadAndConvert(ReaderInterface& reader, WriterInterface& writer, const aron::typenavigator::NavigatorPtr& expectedStructure) { - type::Descriptor t_desc = expectedStructure != nullptr ? expectedStructure->getDescriptor() : type::eUnknown; + type::Descriptor t_desc = expectedStructure != nullptr ? expectedStructure->getDescriptor() : type::Descriptor::eUnknown; + //std::cout << "Expected Structure: " << type::DESCRIPTOR_TO_STRING(t_desc) << std::endl; data::Descriptor desc = reader.getTypeOfNext(t_desc); switch (desc) { - case data::eDict: + case data::Descriptor::eDict: { int elements = reader.readStartDict(); writer.writeStartDict(); typenavigator::NavigatorPtr childType = nullptr; - if (t_desc == type::eDict) + if (t_desc == type::Descriptor::eDict) { - auto t = typenavigator::DictNavigator::DynamicCast(expectedStructure); + auto t = typenavigator::DictNavigator::DynamicCastAndCheck(expectedStructure); childType = t->getAcceptedType(); } @@ -54,13 +55,13 @@ namespace armarx::aron::dataIO std::string key = reader.readKey(); writer.writeKey(key); - if (t_desc == type::eObject) + if (t_desc == type::Descriptor::eObject) { - auto t = typenavigator::ObjectNavigator::DynamicCast(expectedStructure); + auto t = typenavigator::ObjectNavigator::DynamicCastAndCheck(expectedStructure); childType = t->getMemberType(key); } - Converter::ConvertFromReader(reader, writer, childType); + Converter::ReadAndConvert(reader, writer, childType); } writer.writeEndDict(); @@ -68,62 +69,85 @@ namespace armarx::aron::dataIO break; } - case data::eList: + case data::Descriptor::eList: { int elements = reader.readStartList(); writer.writeStartList(); typenavigator::NavigatorPtr childType = nullptr; - if (t_desc == type::eList) + if (t_desc == type::Descriptor::eList) { - auto t = typenavigator::ListNavigator::DynamicCast(expectedStructure); + auto t = typenavigator::ListNavigator::DynamicCastAndCheck(expectedStructure); childType = t->getAcceptedType(); } for (int i = 0; i < elements; ++i) { - if (t_desc == type::eObject) + if (t_desc == type::Descriptor::eObject) { - auto t = typenavigator::TupleNavigator::DynamicCast(expectedStructure); + auto t = typenavigator::TupleNavigator::DynamicCastAndCheck(expectedStructure); childType = t->getAcceptedType(i); } - Converter::ConvertFromReader(reader, writer, childType); + Converter::ReadAndConvert(reader, writer, childType); } writer.writeEndList(); reader.readEndList(); break; } -#define RUN_ARON_MACRO(upperType, lowerType, capsType) \ -case data::e##upperType: \ -{ \ - auto [dims, type] = reader.readStart##upperType(); \ - int elements = std::accumulate(std::begin(dims), std::end(dims), 1, std::multiplies<int>()); \ - std::vector<unsigned char> data(elements); \ - reader.readEnd##upperType(data.data()); \ - \ - writer.write##upperType(dims, type, data.data()); \ - break; \ -} - HANDLE_COMPLEX_DATA -#undef RUN_ARON_MACRO + case data::Descriptor::eNDArray: + { + auto [dims, type] = reader.readStartNDArray(); + int elements = std::accumulate(std::begin(dims), std::end(dims), 1, std::multiplies<int>()); + std::vector<unsigned char> data(elements); + reader.readEndNDArray(data.data()); -#define RUN_ARON_MACRO(upperType, lowerType, capsType) \ -case data::e##upperType: \ -{ \ - lowerType val = reader.readPrimitive<lowerType>(); \ - writer.writePrimitive(val); \ - break; \ -} + writer.writeNDArray(dims, type, data.data()); + break; + } - HANDLE_PRIMITIVE_DATA -#undef RUN_ARON_MACRO + case data::Descriptor::eInt: + { + int val = reader.readPrimitive<int>(); + writer.writePrimitive(val); + break; + } + case data::Descriptor::eLong: + { + long val = reader.readPrimitive<long>(); + writer.writePrimitive(val); + break; + } + case data::Descriptor::eFloat: + { + float val = reader.readPrimitive<float>(); + writer.writePrimitive(val); + break; + } + case data::Descriptor::eDouble: + { + double val = reader.readPrimitive<double>(); + writer.writePrimitive(val); + break; + } + case data::Descriptor::eString: + { + std::string val = reader.readPrimitive<std::string>(); + writer.writePrimitive(val); + break; + } + case data::Descriptor::eBool: + { + bool val = reader.readPrimitive<bool>(); + writer.writePrimitive(val); + break; + } default: { - throw error::DescriptorNotValidException("LegacyAronDataReader", "SetupReaderAndGetResult", "Data-Type could not be resolved", desc); + throw error::DescriptorNotValidException("Converter", "ReadAndConvert", "Data-Type could not be resolved", desc); } } } diff --git a/source/RobotAPI/libraries/aron/core/io/dataIO/converter/Converter.h b/source/RobotAPI/libraries/aron/core/io/dataIO/converter/Converter.h index d51d81761b764d5616bb70e5cefd67dd105987bd..1ea6c6f5c3bf984d2fad6b8ffd55f7cc7d50f76c 100644 --- a/source/RobotAPI/libraries/aron/core/io/dataIO/converter/Converter.h +++ b/source/RobotAPI/libraries/aron/core/io/dataIO/converter/Converter.h @@ -43,6 +43,6 @@ namespace armarx::aron::dataIO Converter() = delete; public: - static void ConvertFromReader(ReaderInterface&, WriterInterface&, const aron::typenavigator::NavigatorPtr& expectedStructure = nullptr); + static void ReadAndConvert(ReaderInterface&, WriterInterface&, const aron::typenavigator::NavigatorPtr& expectedStructure = nullptr); }; } diff --git a/source/RobotAPI/libraries/aron/core/io/dataIO/reader/ReaderToken.h b/source/RobotAPI/libraries/aron/core/io/dataIO/reader/ReaderToken.h index a757d2778ca04857fb436977bcec6e4eb9de3710..b1c8e774e9b252bb582ba7a7dbf2c38c8f158122 100644 --- a/source/RobotAPI/libraries/aron/core/io/dataIO/reader/ReaderToken.h +++ b/source/RobotAPI/libraries/aron/core/io/dataIO/reader/ReaderToken.h @@ -45,7 +45,7 @@ namespace armarx::aron::dataIO // Interface - virtual data::Descriptor getTypeOfNext(const type::Descriptor hint = type::eUnknown) const = 0; + virtual data::Descriptor getTypeOfNext(const type::Descriptor hint = type::Descriptor::eUnknown) const = 0; virtual ElementTypename getNextElement() const = 0; // General implementation @@ -115,7 +115,7 @@ namespace armarx::aron::dataIO protected: // members - data::Descriptor descriptor = data::eUnknown; + data::Descriptor descriptor = data::Descriptor::eUnknown; ElementTypename element; unsigned int childrenSize = 0; diff --git a/source/RobotAPI/libraries/aron/core/io/dataIO/reader/navigator/NavigatorReader.cpp b/source/RobotAPI/libraries/aron/core/io/dataIO/reader/navigator/NavigatorReader.cpp index aa5d3d14864aff4fd5d86b8cfc47b06a81cc0200..2dc7c3db842d4e7deb5ee1c5d94b4be5618f2e64 100644 --- a/source/RobotAPI/libraries/aron/core/io/dataIO/reader/navigator/NavigatorReader.cpp +++ b/source/RobotAPI/libraries/aron/core/io/dataIO/reader/navigator/NavigatorReader.cpp @@ -72,7 +72,7 @@ namespace armarx::aron::dataIO::reader auto current_nav = getNextAndIncrease(); auto current_nav_casted = datanavigator::DictNavigator::DynamicCastAndCheck(current_nav); int c = current_nav->childrenSize(); - auto newToken = std::make_shared<NavigatorReaderToken>(data::eDict, current_nav_casted); + auto newToken = std::make_shared<NavigatorReaderToken>(data::Descriptor::eDict, current_nav_casted); stack.push(newToken); return c; } @@ -95,7 +95,7 @@ namespace armarx::aron::dataIO::reader auto current_nav = getNextAndIncrease(); auto current_nav_casted = datanavigator::ListNavigator::DynamicCastAndCheck(current_nav); int c = current_nav->childrenSize(); - auto newToken = std::make_shared<NavigatorReaderToken>(data::eList, current_nav_casted); + auto newToken = std::make_shared<NavigatorReaderToken>(data::Descriptor::eList, current_nav_casted); stack.push(newToken); return c; } @@ -192,6 +192,17 @@ namespace armarx::aron::dataIO::reader // Helper functions data::Descriptor NavigatorReader::getTypeOfNext(const type::Descriptor hint) const { + if (stack.empty()) + { + if (hint == type::Descriptor::eUnknown) + { + return data::Descriptor::eDict; + } + else + { + return Resolver::GetCorresponding(hint); + } + } auto token = stack.top(); return token->getTypeOfNext(hint); } diff --git a/source/RobotAPI/libraries/aron/core/io/dataIO/reader/navigator/NavigatorReader.h b/source/RobotAPI/libraries/aron/core/io/dataIO/reader/navigator/NavigatorReader.h index 0bcc56b7bdc6e22775fc2d4345e1f9715e942d1f..db52ad1d85c2f10807d10f63bc44c7de717e6b97 100644 --- a/source/RobotAPI/libraries/aron/core/io/dataIO/reader/navigator/NavigatorReader.h +++ b/source/RobotAPI/libraries/aron/core/io/dataIO/reader/navigator/NavigatorReader.h @@ -66,7 +66,7 @@ namespace armarx::aron::dataIO::reader virtual std::string readKey() override; virtual void loadMember(const std::string&) override; - virtual data::Descriptor getTypeOfNext(const type::Descriptor hint = type::eUnknown) const override; + virtual data::Descriptor getTypeOfNext(const type::Descriptor hint = type::Descriptor::eUnknown) const override; private: datanavigator::NavigatorPtr getNext(); diff --git a/source/RobotAPI/libraries/aron/core/io/dataIO/reader/navigator/NavigatorReaderToken.h b/source/RobotAPI/libraries/aron/core/io/dataIO/reader/navigator/NavigatorReaderToken.h index 2efb3352f203d93fa0b647ea318affea7d41b4fd..4b85fe7725b3840c2e9c2b87a5d6cc9c48f9e63f 100644 --- a/source/RobotAPI/libraries/aron/core/io/dataIO/reader/navigator/NavigatorReaderToken.h +++ b/source/RobotAPI/libraries/aron/core/io/dataIO/reader/navigator/NavigatorReaderToken.h @@ -69,7 +69,7 @@ namespace armarx::aron::dataIO::reader } } - data::Descriptor getTypeOfNext(const type::Descriptor hint = type::eUnknown) const override + data::Descriptor getTypeOfNext(const type::Descriptor hint = type::Descriptor::eUnknown) const override { const datanavigator::NavigatorPtr next = getNextElement(); return next->getDescriptor(); diff --git a/source/RobotAPI/libraries/aron/core/io/dataIO/reader/nlohmannJSON/NlohmannJSONReader.cpp b/source/RobotAPI/libraries/aron/core/io/dataIO/reader/nlohmannJSON/NlohmannJSONReader.cpp index 9b15c88280210b4e9b2e583ba7439d87e68909d9..c243c4e4beaf851090607423dd91e1d5ade4118a 100644 --- a/source/RobotAPI/libraries/aron/core/io/dataIO/reader/nlohmannJSON/NlohmannJSONReader.cpp +++ b/source/RobotAPI/libraries/aron/core/io/dataIO/reader/nlohmannJSON/NlohmannJSONReader.cpp @@ -70,7 +70,7 @@ namespace armarx::aron::dataIO::reader { nlohmann::json current_json = getNextAndIncrease(); int c = current_json.size(); - auto newToken = std::make_shared<NlohmannJSONReaderToken>(data::eDict, current_json); + auto newToken = std::make_shared<NlohmannJSONReaderToken>(data::Descriptor::eDict, current_json); stack.push(newToken); return c; } @@ -78,7 +78,7 @@ namespace armarx::aron::dataIO::reader bool NlohmannJSONReader::readEndDict() { auto token = stack.top(); - token->assertType(data::eDict); + token->assertType(data::Descriptor::eDict); if (token->finishedElement()) { @@ -92,7 +92,7 @@ namespace armarx::aron::dataIO::reader { nlohmann::json current_json = getNextAndIncrease(); int c = current_json.size(); - auto newToken = std::make_shared<NlohmannJSONReaderToken>(data::eList, current_json); + auto newToken = std::make_shared<NlohmannJSONReaderToken>(data::Descriptor::eList, current_json); stack.push(newToken); return c; } @@ -100,7 +100,7 @@ namespace armarx::aron::dataIO::reader bool NlohmannJSONReader::readEndList() { auto token = stack.top(); - token->assertType(data::eList); + token->assertType(data::Descriptor::eList); if (token->finishedElement()) { @@ -184,6 +184,17 @@ namespace armarx::aron::dataIO::reader // Helper functions data::Descriptor NlohmannJSONReader::getTypeOfNext(const type::Descriptor hint) const { + if (stack.empty()) + { + if (hint == type::Descriptor::eUnknown) + { + return data::Descriptor::eDict; + } + else + { + return Resolver::GetCorresponding(hint); + } + } auto token = stack.top(); return token->getTypeOfNext(hint); } diff --git a/source/RobotAPI/libraries/aron/core/io/dataIO/reader/nlohmannJSON/NlohmannJSONReader.h b/source/RobotAPI/libraries/aron/core/io/dataIO/reader/nlohmannJSON/NlohmannJSONReader.h index 1ca1810a0c3085e4d53b7a79c934dc1eaa7e1e25..7749530308b806da5898881879cef6df26143358 100644 --- a/source/RobotAPI/libraries/aron/core/io/dataIO/reader/nlohmannJSON/NlohmannJSONReader.h +++ b/source/RobotAPI/libraries/aron/core/io/dataIO/reader/nlohmannJSON/NlohmannJSONReader.h @@ -64,7 +64,7 @@ namespace armarx::aron::dataIO::reader virtual std::string readKey() override; virtual void loadMember(const std::string&) override; - virtual data::Descriptor getTypeOfNext(const type::Descriptor hint = type::eUnknown) const override; + virtual data::Descriptor getTypeOfNext(const type::Descriptor hint = type::Descriptor::eUnknown) const override; private: nlohmann::json getNext(); diff --git a/source/RobotAPI/libraries/aron/core/io/dataIO/reader/nlohmannJSON/NlohmannJSONReaderToken.h b/source/RobotAPI/libraries/aron/core/io/dataIO/reader/nlohmannJSON/NlohmannJSONReaderToken.h index d155a2d155027ad03f16a359a903da88dae6776c..04acd920b51789d2ce925f8aab48c268baf3fed7 100644 --- a/source/RobotAPI/libraries/aron/core/io/dataIO/reader/nlohmannJSON/NlohmannJSONReaderToken.h +++ b/source/RobotAPI/libraries/aron/core/io/dataIO/reader/nlohmannJSON/NlohmannJSONReaderToken.h @@ -57,7 +57,7 @@ namespace armarx::aron::dataIO::reader switch (descriptor) { - case data::eDict: + case data::Descriptor::eDict: { for (auto it = data.begin(); it != data.end(); ++it) { @@ -66,7 +66,7 @@ namespace armarx::aron::dataIO::reader childrenSize = data.size(); break; } - case data::eList: + case data::Descriptor::eList: { childrenSize = data.size(); break; @@ -84,36 +84,36 @@ namespace armarx::aron::dataIO::reader // Check if specific NDArray key exists if (next.find(io::Data::READER_WRITER_NDARRAY_DATA_SLUG) != next.end()) { - return data::eNDArray; + return data::Descriptor::eNDArray; } - return data::eDict; + return data::Descriptor::eDict; } if (next.is_array()) { - return data::eList; + return data::Descriptor::eList; } if (next.is_number_integer()) { data::Descriptor d = Resolver::GetFirstIfRelated( Resolver::GetCorresponding(hint), - data::eLong); + data::Descriptor::eLong); return d; } if (next.is_number_float()) { data::Descriptor d = Resolver::GetFirstIfRelated( Resolver::GetCorresponding(hint), - data::eDouble); + data::Descriptor::eDouble); return d; } if (next.is_boolean()) { - return data::eBool; + return data::Descriptor::eBool; } if (next.is_string()) { - return data::eString; + return data::Descriptor::eString; } throw error::AronException("NlohmannJSONReaderToken", "getTypeOfNextElement", "Could not determine the type of an nlohmann::json object. Could not convert to data::Descriptor enum."); } @@ -122,12 +122,12 @@ namespace armarx::aron::dataIO::reader { switch (descriptor) { - case data::eDict: + case data::Descriptor::eDict: { nlohmann::json ret = element[getCurrentKey()]; return ret; } - case data::eList: + case data::Descriptor::eList: { nlohmann::json ret = element[currentIndex]; return ret; diff --git a/source/RobotAPI/libraries/aron/core/io/dataIO/visitor/Visitor.cpp b/source/RobotAPI/libraries/aron/core/io/dataIO/visitor/Visitor.cpp index 9f2dd3cd6e470c72698aae1c5c0bdcd948194e53..b5be280a8cfe72963afa63b88a900b6885250c33 100644 --- a/source/RobotAPI/libraries/aron/core/io/dataIO/visitor/Visitor.cpp +++ b/source/RobotAPI/libraries/aron/core/io/dataIO/visitor/Visitor.cpp @@ -33,76 +33,76 @@ namespace armarx::aron::dataIO { - void Visitor::SetupWriterFromAronDataPtr(WriterInterface& writer, const datanavigator::NavigatorPtr& aron) + void Visitor::VisitAndSetup(WriterInterface& writer, const datanavigator::NavigatorPtr& aron) { - SetupWriterFromAronDataPtr(writer, aron->getResult()); + VisitAndSetup(writer, aron->getResult()); } - void Visitor::SetupWriterFromAronDataPtr(WriterInterface& writer, const data::AronDataPtr& aron) + void Visitor::VisitAndSetup(WriterInterface& writer, const data::AronDataPtr& aron) { data::Descriptor desc = Resolver::GetDescriptor(aron); switch (desc) { - case data::eDict: + case data::Descriptor::eDict: { data::AronDictPtr casted = data::AronDictPtr::dynamicCast(aron); writer.writeStartDict(); for (const auto& [key, value] : casted->elements) { writer.writeKey(key); - Visitor::SetupWriterFromAronDataPtr(writer, value); + Visitor::VisitAndSetup(writer, value); } writer.writeEndDict(); break; } - case data::eList: + case data::Descriptor::eList: { data::AronListPtr casted = data::AronListPtr::dynamicCast(aron); writer.writeStartList(); for (const auto& value : casted->elements) { - Visitor::SetupWriterFromAronDataPtr(writer, value); + Visitor::VisitAndSetup(writer, value); } writer.writeEndList(); break; } - case data::eNDArray: + case data::Descriptor::eNDArray: { data::AronNDArrayPtr casted = data::AronNDArrayPtr::dynamicCast(aron); writer.writeNDArray(casted->dimensions, casted->type, casted->data.data()); break; } - case data::eInt: + case data::Descriptor::eInt: { data::AronIntPtr casted = data::AronIntPtr::dynamicCast(aron); writer.writePrimitive(casted->value); break; } - case data::eLong: + case data::Descriptor::eLong: { data::AronLongPtr casted = data::AronLongPtr::dynamicCast(aron); writer.writePrimitive(casted->value); break; } - case data::eFloat: + case data::Descriptor::eFloat: { data::AronFloatPtr casted = data::AronFloatPtr::dynamicCast(aron); writer.writePrimitive(casted->value); break; } - case data::eDouble: + case data::Descriptor::eDouble: { data::AronDoublePtr casted = data::AronDoublePtr::dynamicCast(aron); writer.writePrimitive(casted->value); break; } - case data::eString: + case data::Descriptor::eString: { data::AronStringPtr casted = data::AronStringPtr::dynamicCast(aron); writer.writePrimitive(casted->value); break; } - case data::eBool: + case data::Descriptor::eBool: { data::AronBoolPtr casted = data::AronBoolPtr::dynamicCast(aron); writer.writePrimitive(casted->value); diff --git a/source/RobotAPI/libraries/aron/core/io/dataIO/visitor/Visitor.h b/source/RobotAPI/libraries/aron/core/io/dataIO/visitor/Visitor.h index b45ef50c60207e97e6e29e170df39cf0be237a90..b6b00cbbc7d55ff95c3a1674af3dd7d6b9b28e29 100644 --- a/source/RobotAPI/libraries/aron/core/io/dataIO/visitor/Visitor.h +++ b/source/RobotAPI/libraries/aron/core/io/dataIO/visitor/Visitor.h @@ -41,8 +41,8 @@ namespace armarx::aron::dataIO Visitor() = delete; public: - static void SetupWriterFromAronDataPtr(WriterInterface&, const datanavigator::NavigatorPtr&); - static void SetupWriterFromAronDataPtr(WriterInterface&, const data::AronDataPtr&); + static void VisitAndSetup(WriterInterface&, const datanavigator::NavigatorPtr&); + static void VisitAndSetup(WriterInterface&, const data::AronDataPtr&); public: }; diff --git a/source/RobotAPI/libraries/aron/core/io/dataIO/writer/WriterToken.h b/source/RobotAPI/libraries/aron/core/io/dataIO/writer/WriterToken.h index 950baf3f13359a2ff38db78a16af0c73e24d303e..f91f6c0404fa5f1efaca3301b754165e98abebc8 100644 --- a/source/RobotAPI/libraries/aron/core/io/dataIO/writer/WriterToken.h +++ b/source/RobotAPI/libraries/aron/core/io/dataIO/writer/WriterToken.h @@ -71,9 +71,9 @@ namespace armarx::aron::dataIO data::Descriptor desc = this->getDescriptor(); switch (desc) { - case data::eDict: + case data::Descriptor::eDict: return currentKey; - case data::eList: + case data::Descriptor::eList: return std::to_string(currentIndex); default: throw error::DescriptorNotValidException("NavigatorWriterToken", "toElementAccessor", "Could not resove a type of a navigator. Allowed are only containers.", desc); @@ -82,7 +82,7 @@ namespace armarx::aron::dataIO protected: // members - data::Descriptor descriptor = data::eUnknown; + data::Descriptor descriptor = data::Descriptor::eUnknown; ElementTypename element; // current index diff --git a/source/RobotAPI/libraries/aron/core/io/dataIO/writer/navigator/NavigatorWriter.cpp b/source/RobotAPI/libraries/aron/core/io/dataIO/writer/navigator/NavigatorWriter.cpp index adebb69a3a86875ac18e9854c96256c01458a9a3..15f57ecf56e00bf09720c4250e8972b9f79f546d 100644 --- a/source/RobotAPI/libraries/aron/core/io/dataIO/writer/navigator/NavigatorWriter.cpp +++ b/source/RobotAPI/libraries/aron/core/io/dataIO/writer/navigator/NavigatorWriter.cpp @@ -53,7 +53,7 @@ namespace armarx::aron::dataIO::writer { Path path = generatePath(); auto data = std::make_shared<datanavigator::DictNavigator>(path); - auto new_token = std::make_shared<NavigatorWriterToken>(data::eDict, data); + auto new_token = std::make_shared<NavigatorWriterToken>(data::Descriptor::eDict, data); stack.push(new_token); } @@ -73,7 +73,7 @@ namespace armarx::aron::dataIO::writer { Path path = generatePath(); auto data = std::make_shared<datanavigator::ListNavigator>(path); - auto new_token = std::make_shared<NavigatorWriterToken>(data::eList, data); + auto new_token = std::make_shared<NavigatorWriterToken>(data::Descriptor::eList, data); stack.push(new_token); } diff --git a/source/RobotAPI/libraries/aron/core/io/dataIO/writer/nlohmannJSON/NlohmannJSONWriter.cpp b/source/RobotAPI/libraries/aron/core/io/dataIO/writer/nlohmannJSON/NlohmannJSONWriter.cpp index e57ee04fd96febf4aeeb128385ac14dce87d9217..b768c5da072915d37406b2c0d7f3fb9bb5839dd9 100644 --- a/source/RobotAPI/libraries/aron/core/io/dataIO/writer/nlohmannJSON/NlohmannJSONWriter.cpp +++ b/source/RobotAPI/libraries/aron/core/io/dataIO/writer/nlohmannJSON/NlohmannJSONWriter.cpp @@ -32,7 +32,7 @@ namespace armarx::aron::dataIO::writer void NlohmannJSONWriter::writeStartDict() { nlohmann::json data; - auto new_token = std::make_shared<NlohmannJSONWriterToken>(data::eDict, data); + auto new_token = std::make_shared<NlohmannJSONWriterToken>(data::Descriptor::eDict, data); stack.push(new_token); } @@ -51,7 +51,7 @@ namespace armarx::aron::dataIO::writer void NlohmannJSONWriter::writeStartList() { nlohmann::json data; - auto new_token = std::make_shared<NlohmannJSONWriterToken>(data::eList, data); + auto new_token = std::make_shared<NlohmannJSONWriterToken>(data::Descriptor::eList, data); stack.push(new_token); } diff --git a/source/RobotAPI/libraries/aron/core/io/typeIO/converter/Converter.cpp b/source/RobotAPI/libraries/aron/core/io/typeIO/converter/Converter.cpp index b9aca9ffceea3bbae3fbd76794112bdca58379d8..48decff3a1763338b8d2de06c217bfa38b60cf86 100644 --- a/source/RobotAPI/libraries/aron/core/io/typeIO/converter/Converter.cpp +++ b/source/RobotAPI/libraries/aron/core/io/typeIO/converter/Converter.cpp @@ -27,12 +27,12 @@ namespace armarx::aron::typeIO { - void Converter::ConvertFromReader(ReaderInterface& reader, WriterInterface& writer) + void Converter::ReadAndConvert(ReaderInterface& reader, WriterInterface& writer) { type::Descriptor desc = reader.getTypeOfNext(); switch (desc) { - case type::eObject: + case type::Descriptor::eObject: { const auto [name, elements] = reader.readStartObject(); writer.writeStartObject(name); @@ -41,134 +41,134 @@ namespace armarx::aron::typeIO { std::string key = reader.readKey(); writer.writeKey(key); - Converter::ConvertFromReader(reader, writer); + Converter::ReadAndConvert(reader, writer); } writer.writeEndObject(); reader.readEndObject(); break; } - case type::eDict: + case type::Descriptor::eDict: { reader.readStartDict(); writer.writeStartDict(); - Converter::ConvertFromReader(reader, writer); + Converter::ReadAndConvert(reader, writer); writer.writeEndDict(); reader.readEndDict(); break; } - case type::eTuple: + case type::Descriptor::eTuple: { int elements = reader.readStartTuple(); writer.writeStartTuple(); for (int i = 0; i < elements; ++i) { - Converter::ConvertFromReader(reader, writer); + Converter::ReadAndConvert(reader, writer); } writer.writeEndTuple(); reader.readEndTuple(); break; } - case type::eList: + case type::Descriptor::eList: { reader.readStartList(); writer.writeStartList(); - Converter::ConvertFromReader(reader, writer); + Converter::ReadAndConvert(reader, writer); writer.writeEndList(); reader.readEndList(); break; } - case type::eEigenMatrix: + case type::Descriptor::eEigenMatrix: { auto x = reader.readEigenMatrix(); writer.writeEigenMatrix(std::get<0>(x), std::get<1>(x)); break; } - case type::eEigenQuaternion: + case type::Descriptor::eEigenQuaternion: { auto x = reader.readEigenQuaternion(); writer.writeEigenQuaternion(x); break; } - case type::eIVTCByteImage: + case type::Descriptor::eIVTCByteImage: { auto x = reader.readIVTCByteImage(); writer.writeIVTCByteImage(std::get<0>(x), std::get<1>(x), std::get<2>(x)); break; } - case type::eOpenCVMat: + case type::Descriptor::eOpenCVMat: { auto x = reader.readOpenCVMat(); writer.writeOpenCVMat(std::get<0>(x), std::get<1>(x)); break; } - case type::ePCLPointCloud: + case type::Descriptor::ePCLPointCloud: { auto x = reader.readPCLPointCloud(); writer.writePCLPointCloud(std::get<0>(x), std::get<1>(x), std::get<2>(x)); break; } - case type::ePosition: + case type::Descriptor::ePosition: { reader.readPosition(); writer.writePosition(); break; } - case type::eOrientation: + case type::Descriptor::eOrientation: { reader.readOrientation(); writer.writeOrientation(); break; } - case type::ePose: + case type::Descriptor::ePose: { reader.readPose(); writer.writePose(); break; } - case type::eInt: + case type::Descriptor::eInt: { reader.readInt(); writer.writeInt(); break; } - case type::eLong: + case type::Descriptor::eLong: { reader.readLong(); writer.writeLong(); break; } - case type::eFloat: + case type::Descriptor::eFloat: { reader.readFloat(); writer.writeFloat(); break; } - case type::eDouble: + case type::Descriptor::eDouble: { reader.readDouble(); writer.writeDouble(); break; } - case type::eString: + case type::Descriptor::eString: { reader.readString(); writer.writeString(); break; } - case type::eBool: + case type::Descriptor::eBool: { reader.readBool(); writer.writeBool(); break; } - case type::eTime: + case type::Descriptor::eTime: { reader.readTime(); writer.writeTime(); diff --git a/source/RobotAPI/libraries/aron/core/io/typeIO/converter/Converter.h b/source/RobotAPI/libraries/aron/core/io/typeIO/converter/Converter.h index f1c59c61894ff07dfdea24d1f5682620392ebf35..8ef1007efb1d06ac2b0360ccc8008f7fdfa634d2 100644 --- a/source/RobotAPI/libraries/aron/core/io/typeIO/converter/Converter.h +++ b/source/RobotAPI/libraries/aron/core/io/typeIO/converter/Converter.h @@ -45,7 +45,7 @@ namespace armarx::aron::typeIO Converter() = delete; public: - static void ConvertFromReader(ReaderInterface&, WriterInterface&); + static void ReadAndConvert(ReaderInterface&, WriterInterface&); public: }; diff --git a/source/RobotAPI/libraries/aron/core/io/typeIO/reader/ReaderToken.h b/source/RobotAPI/libraries/aron/core/io/typeIO/reader/ReaderToken.h index c4487c6baee1fd033932c276dc114891f274d575..17b364ff4874a397820cf3143fb180cf21cd8275 100644 --- a/source/RobotAPI/libraries/aron/core/io/typeIO/reader/ReaderToken.h +++ b/source/RobotAPI/libraries/aron/core/io/typeIO/reader/ReaderToken.h @@ -54,8 +54,8 @@ namespace armarx::aron::typeIO { switch (descriptor) { - case type::eObject: - case type::eIntEnum: + case type::Descriptor::eObject: + case type::Descriptor::eIntEnum: { return elementName; } @@ -125,7 +125,7 @@ namespace armarx::aron::typeIO protected: // members - type::Descriptor descriptor = type::eUnknown; + type::Descriptor descriptor = type::Descriptor::eUnknown; ElementTypename element; std::string elementName = ""; diff --git a/source/RobotAPI/libraries/aron/core/io/typeIO/reader/navigator/NavigatorReader.cpp b/source/RobotAPI/libraries/aron/core/io/typeIO/reader/navigator/NavigatorReader.cpp index 19a19936f8cc8e01f494c00105735a6556c1ef14..0effe2a60983b988abd7c3e8ae8191f69e30ee0d 100644 --- a/source/RobotAPI/libraries/aron/core/io/typeIO/reader/navigator/NavigatorReader.cpp +++ b/source/RobotAPI/libraries/aron/core/io/typeIO/reader/navigator/NavigatorReader.cpp @@ -59,7 +59,7 @@ namespace armarx::aron::typeIO::reader { auto current_nav = getNextAndIncrease(); auto current_nav_casted = typenavigator::ObjectNavigator::DynamicCastAndCheck(current_nav); - auto newToken = std::make_shared<NavigatorReaderToken>(type::eObject, current_nav_casted); + auto newToken = std::make_shared<NavigatorReaderToken>(type::Descriptor::eObject, current_nav_casted); stack.push(newToken); return {newToken->getElementName(), newToken->getElementChildrenSize()}; } @@ -67,7 +67,7 @@ namespace armarx::aron::typeIO::reader bool NavigatorReader::readEndObject() { auto token = stack.top(); - token->assertType(type::eObject); + token->assertType(type::Descriptor::eObject); if (token->finishedElement()) { @@ -81,7 +81,7 @@ namespace armarx::aron::typeIO::reader { auto current_nav = getNextAndIncrease(); auto current_nav_casted = typenavigator::DictNavigator::DynamicCastAndCheck(current_nav); - auto newToken = std::make_shared<NavigatorReaderToken>(type::eDict, current_nav_casted); + auto newToken = std::make_shared<NavigatorReaderToken>(type::Descriptor::eDict, current_nav_casted); stack.push(newToken); return newToken->getElementChildrenSize(); } @@ -89,7 +89,7 @@ namespace armarx::aron::typeIO::reader bool NavigatorReader::readEndDict() { auto token = stack.top(); - token->assertType(type::eDict); + token->assertType(type::Descriptor::eDict); if (token->finishedElement()) { @@ -103,7 +103,7 @@ namespace armarx::aron::typeIO::reader { auto current_nav = getNextAndIncrease(); auto current_nav_casted = typenavigator::ListNavigator::DynamicCastAndCheck(current_nav); - auto newToken = std::make_shared<NavigatorReaderToken>(type::eList, current_nav_casted); + auto newToken = std::make_shared<NavigatorReaderToken>(type::Descriptor::eList, current_nav_casted); stack.push(newToken); return newToken->getElementChildrenSize(); } @@ -111,7 +111,7 @@ namespace armarx::aron::typeIO::reader bool NavigatorReader::readEndList() { auto token = stack.top(); - token->assertType(type::eList); + token->assertType(type::Descriptor::eList); if (token->finishedElement()) { @@ -125,7 +125,7 @@ namespace armarx::aron::typeIO::reader { auto current_nav = getNextAndIncrease(); auto current_nav_casted = typenavigator::TupleNavigator::DynamicCastAndCheck(current_nav); - auto newToken = std::make_shared<NavigatorReaderToken>(type::eTuple, current_nav_casted); + auto newToken = std::make_shared<NavigatorReaderToken>(type::Descriptor::eTuple, current_nav_casted); stack.push(newToken); return newToken->getElementChildrenSize(); } @@ -133,7 +133,7 @@ namespace armarx::aron::typeIO::reader bool NavigatorReader::readEndTuple() { auto token = stack.top(); - token->assertType(type::eTuple); + token->assertType(type::Descriptor::eTuple); if (token->finishedElement()) { @@ -147,7 +147,7 @@ namespace armarx::aron::typeIO::reader { auto current_nav = getNextAndIncrease(); auto current_nav_casted = typenavigator::PairNavigator::DynamicCastAndCheck(current_nav); - auto newToken = std::make_shared<NavigatorReaderToken>(type::ePair, current_nav_casted); + auto newToken = std::make_shared<NavigatorReaderToken>(type::Descriptor::ePair, current_nav_casted); stack.push(newToken); return newToken->getElementChildrenSize(); } @@ -155,7 +155,7 @@ namespace armarx::aron::typeIO::reader bool NavigatorReader::readEndPair() { auto token = stack.top(); - token->assertType(type::ePair); + token->assertType(type::Descriptor::ePair); if (token->finishedElement()) { diff --git a/source/RobotAPI/libraries/aron/core/io/typeIO/reader/nlohmannJSON/NlohmannJSONReader.cpp b/source/RobotAPI/libraries/aron/core/io/typeIO/reader/nlohmannJSON/NlohmannJSONReader.cpp index eea8c5dc279d527d9aa6024b1c3bfed2f2e9da8a..98d6953ade3f36ca2408dc379a3b325e8fd007de 100644 --- a/source/RobotAPI/libraries/aron/core/io/typeIO/reader/nlohmannJSON/NlohmannJSONReader.cpp +++ b/source/RobotAPI/libraries/aron/core/io/typeIO/reader/nlohmannJSON/NlohmannJSONReader.cpp @@ -40,7 +40,7 @@ namespace armarx::aron::typeIO::reader } NlohmannJSONReader::NlohmannJSONReader(const std::string& n) : - input(n) + input(nlohmann::json::parse(n)) { } @@ -58,7 +58,7 @@ namespace armarx::aron::typeIO::reader std::tuple<std::string, int> NlohmannJSONReader::readStartObject() { nlohmann::json current_json = getNextAndIncrease(); - auto newToken = std::make_shared<NlohmannJSONReaderToken>(type::eObject, current_json); + auto newToken = std::make_shared<NlohmannJSONReaderToken>(type::Descriptor::eObject, current_json); stack.push(newToken); return {newToken->getElementName(), newToken->getElementChildrenSize()}; } @@ -66,7 +66,7 @@ namespace armarx::aron::typeIO::reader bool NlohmannJSONReader::readEndObject() { NlohmannJSONReaderTokenPtr token = stack.top(); - token->assertType(type::eObject); + token->assertType(type::Descriptor::eObject); if (token->finishedElement()) { @@ -79,7 +79,7 @@ namespace armarx::aron::typeIO::reader int NlohmannJSONReader::readStartDict() { nlohmann::json current_json = getNextAndIncrease(); - auto newToken = std::make_shared<NlohmannJSONReaderToken>(type::eDict, current_json); + auto newToken = std::make_shared<NlohmannJSONReaderToken>(type::Descriptor::eDict, current_json); stack.push(newToken); return newToken->getElementChildrenSize(); } @@ -87,7 +87,7 @@ namespace armarx::aron::typeIO::reader bool NlohmannJSONReader::readEndDict() { NlohmannJSONReaderTokenPtr token = stack.top(); - token->assertType(type::eDict); + token->assertType(type::Descriptor::eDict); if (token->finishedElement()) { @@ -100,7 +100,7 @@ namespace armarx::aron::typeIO::reader int NlohmannJSONReader::readStartList() { nlohmann::json current_json = getNextAndIncrease(); - auto newToken = std::make_shared<NlohmannJSONReaderToken>(type::eList, current_json); + auto newToken = std::make_shared<NlohmannJSONReaderToken>(type::Descriptor::eList, current_json); stack.push(newToken); return newToken->getElementChildrenSize(); } @@ -108,7 +108,7 @@ namespace armarx::aron::typeIO::reader bool NlohmannJSONReader::readEndList() { NlohmannJSONReaderTokenPtr token = stack.top(); - token->assertType(type::eList); + token->assertType(type::Descriptor::eList); if (token->finishedElement()) { @@ -121,7 +121,7 @@ namespace armarx::aron::typeIO::reader int NlohmannJSONReader::readStartTuple() { nlohmann::json current_json = getNextAndIncrease(); - auto newToken = std::make_shared<NlohmannJSONReaderToken>(type::eTuple, current_json); + auto newToken = std::make_shared<NlohmannJSONReaderToken>(type::Descriptor::eTuple, current_json); stack.push(newToken); return newToken->getElementChildrenSize(); } @@ -129,7 +129,7 @@ namespace armarx::aron::typeIO::reader bool NlohmannJSONReader::readEndTuple() { NlohmannJSONReaderTokenPtr token = stack.top(); - token->assertType(type::eTuple); + token->assertType(type::Descriptor::eTuple); if (token->finishedElement()) { @@ -142,7 +142,7 @@ namespace armarx::aron::typeIO::reader int NlohmannJSONReader::readStartPair() { nlohmann::json current_json = getNextAndIncrease(); - auto newToken = std::make_shared<NlohmannJSONReaderToken>(type::ePair, current_json); + auto newToken = std::make_shared<NlohmannJSONReaderToken>(type::Descriptor::ePair, current_json); stack.push(newToken); return newToken->getElementChildrenSize(); } @@ -150,7 +150,7 @@ namespace armarx::aron::typeIO::reader bool NlohmannJSONReader::readEndPair() { NlohmannJSONReaderTokenPtr token = stack.top(); - token->assertType(type::ePair); + token->assertType(type::Descriptor::ePair); if (token->finishedElement()) { @@ -268,6 +268,11 @@ namespace armarx::aron::typeIO::reader // Helper functions type::Descriptor NlohmannJSONReader::getTypeOfNext() const { + if (stack.empty()) + { + return type::Descriptor::eObject; + } + auto token = stack.top(); return token->getTypeOfNext(); } diff --git a/source/RobotAPI/libraries/aron/core/io/typeIO/reader/nlohmannJSON/NlohmannJSONReaderToken.h b/source/RobotAPI/libraries/aron/core/io/typeIO/reader/nlohmannJSON/NlohmannJSONReaderToken.h index 78b3c04ab5fe09cef34cee4c96c5749a9eff908c..3d3503af2567199be5ebf627f45813f2b220c606 100644 --- a/source/RobotAPI/libraries/aron/core/io/typeIO/reader/nlohmannJSON/NlohmannJSONReaderToken.h +++ b/source/RobotAPI/libraries/aron/core/io/typeIO/reader/nlohmannJSON/NlohmannJSONReaderToken.h @@ -57,14 +57,14 @@ namespace armarx::aron::typeIO::reader { case type::Descriptor::eObject: { - for (auto it = type.begin(); it != type.end(); ++it) + for (auto& [key, val] : type.get<nlohmann::json::object_t>()) { - if (it.key() == io::Data::READER_WRITER_NAME_SLUG) + if (key == io::Data::READER_WRITER_NAME_SLUG) { continue; } - allMemberNames.push_back(it.key()); + allMemberNames.push_back(key); } childrenSize = allMemberNames.size(); elementName = element[io::Data::READER_WRITER_NAME_SLUG]; @@ -85,7 +85,7 @@ namespace armarx::aron::typeIO::reader childrenSize = 1; break; } - case type::ePair: + case type::Descriptor::ePair: { childrenSize = 2; break; @@ -103,87 +103,87 @@ namespace armarx::aron::typeIO::reader { if (next.find(io::Data::READER_WRITER_DICT_ACCEPTED_TYPE_SLUG) != next.end()) { - return type::eDict; + return type::Descriptor::eDict; } if (next.find(io::Data::READER_WRITER_LIST_ACCEPTED_TYPE_SLUG) != next.end()) { - return type::eList; + return type::Descriptor::eList; } if (next.find(io::Data::READER_WRITER_INT_ENUM_NAME_SLUG) != next.end()) { - return type::eIntEnum; + return type::Descriptor::eIntEnum; } if (next.find(io::Data::READER_WRITER_NDARRAY_NAME_SLUG) != next.end()) { if (next[io::Data::READER_WRITER_NDARRAY_NAME_SLUG] == "EigenMatrix") { - return type::eEigenMatrix; + return type::Descriptor::eEigenMatrix; } if (next[io::Data::READER_WRITER_NDARRAY_NAME_SLUG] == "EigenQuaternion") { - return type::eEigenQuaternion; + return type::Descriptor::eEigenQuaternion; } if (next[io::Data::READER_WRITER_NDARRAY_NAME_SLUG] == "IVTCByteImage") { - return type::eIVTCByteImage; + return type::Descriptor::eIVTCByteImage; } if (next[io::Data::READER_WRITER_NDARRAY_NAME_SLUG] == "OpenCVMat") { - return type::eOpenCVMat; + return type::Descriptor::eOpenCVMat; } if (next[io::Data::READER_WRITER_NDARRAY_NAME_SLUG] == "PCLPointCloud") { - return type::ePCLPointCloud; + return type::Descriptor::ePCLPointCloud; } if (next[io::Data::READER_WRITER_NDARRAY_NAME_SLUG] == "Position") { - return type::ePosition; + return type::Descriptor::ePosition; } if (next[io::Data::READER_WRITER_NDARRAY_NAME_SLUG] == "Orientation") { - return type::eOrientation; + return type::Descriptor::eOrientation; } if (next[io::Data::READER_WRITER_NDARRAY_NAME_SLUG] == "Pose") { - return type::ePose; + return type::Descriptor::ePose; } throw error::AronException("NlohmannJSONReaderToken", "getTypeOfNextElement", "Could not determine the type of an nlohmann::json object. Found indicator of NDArray but could not resolve real type. Found JSON: " + next[io::Data::READER_WRITER_NDARRAY_NAME_SLUG].dump(2)); } - return type::eObject; + return type::Descriptor::eObject; } if (next.is_array()) { - return type::eTuple; + return type::Descriptor::eTuple; } if (next.is_string()) { if (next == io::Data::READER_WRITER_INT_TYPENAME_SLUG) { - return type::eInt; + return type::Descriptor::eInt; } if (next == io::Data::READER_WRITER_LONG_TYPENAME_SLUG) { - return type::eLong; + return type::Descriptor::eLong; } if (next == io::Data::READER_WRITER_FLOAT_TYPENAME_SLUG) { - return type::eFloat; + return type::Descriptor::eFloat; } if (next == io::Data::READER_WRITER_DOUBLE_TYPENAME_SLUG) { - return type::eDouble; + return type::Descriptor::eDouble; } if (next == io::Data::READER_WRITER_STRING_TYPENAME_SLUG) { - return type::eString; + return type::Descriptor::eString; } if (next == io::Data::READER_WRITER_BOOL_TYPENAME_SLUG) { - return type::eBool; + return type::Descriptor::eBool; } if (next == io::Data::READER_WRITER_TIME_TYPENAME_SLUG) { - return type::eTime; + return type::Descriptor::eTime; } } throw error::AronException("NlohmannJSONReaderToken", "getTypeOfNextElement", "Could not determine the type of an nlohmann::json object. Could not convert to type::Descriptor enum. Found JSON: " + next.dump(2)); diff --git a/source/RobotAPI/libraries/aron/core/io/typeIO/visitor/Visitor.cpp b/source/RobotAPI/libraries/aron/core/io/typeIO/visitor/Visitor.cpp index 99005c64e9a148fad4cbf4b54932d10f68332a5a..1b0bb02c4ea191472b8a5502ade389fefcc30028 100644 --- a/source/RobotAPI/libraries/aron/core/io/typeIO/visitor/Visitor.cpp +++ b/source/RobotAPI/libraries/aron/core/io/typeIO/visitor/Visitor.cpp @@ -33,137 +33,137 @@ namespace armarx::aron::typeIO { - void Visitor::SetupWriterFromAronTypePtr(WriterInterface& writer, const typenavigator::NavigatorPtr& aron) + void Visitor::VisitAndSetup(WriterInterface& writer, const typenavigator::NavigatorPtr& aron) { - SetupWriterFromAronTypePtr(writer, aron->getResult()); + VisitAndSetup(writer, aron->getResult()); } - void Visitor::SetupWriterFromAronTypePtr(WriterInterface& writer, const type::AronTypePtr& aron) + void Visitor::VisitAndSetup(WriterInterface& writer, const type::AronTypePtr& aron) { type::Descriptor desc = Resolver::GetDescriptor(aron); switch (desc) { - case type::eObject: + case type::Descriptor::eObject: { type::AronObjectPtr casted = type::AronObjectPtr::dynamicCast(aron); writer.writeStartObject(casted->objectName); for (const auto& [key, value] : casted->elementTypes) { writer.writeKey(key); - Visitor::SetupWriterFromAronTypePtr(writer, value); + Visitor::VisitAndSetup(writer, value); } writer.writeEndObject(); break; } - case type::eDict: + case type::Descriptor::eDict: { type::AronDictPtr casted = type::AronDictPtr::dynamicCast(aron); writer.writeStartDict(); - Visitor::SetupWriterFromAronTypePtr(writer, casted->acceptedType); + Visitor::VisitAndSetup(writer, casted->acceptedType); writer.writeEndDict(); break; } - case type::eTuple: + case type::Descriptor::eTuple: { type::AronTuplePtr casted = type::AronTuplePtr::dynamicCast(aron); writer.writeStartTuple(); for (const auto& value : casted->elementTypes) { - Visitor::SetupWriterFromAronTypePtr(writer, value); + Visitor::VisitAndSetup(writer, value); } writer.writeEndTuple(); break; } - case type::eList: + case type::Descriptor::eList: { type::AronListPtr casted = type::AronListPtr::dynamicCast(aron); writer.writeStartList(); - Visitor::SetupWriterFromAronTypePtr(writer, casted->acceptedType); + Visitor::VisitAndSetup(writer, casted->acceptedType); writer.writeEndList(); break; } - case type::eEigenMatrix: + case type::Descriptor::eEigenMatrix: { type::AronEigenMatrixPtr casted = type::AronEigenMatrixPtr::dynamicCast(aron); writer.writeEigenMatrix(casted->dimensions, casted->typeName); break; } - case type::eEigenQuaternion: + case type::Descriptor::eEigenQuaternion: { type::AronEigenQuaternionPtr casted = type::AronEigenQuaternionPtr::dynamicCast(aron); writer.writeEigenQuaternion(casted->typeName); break; } - case type::eIVTCByteImage: + case type::Descriptor::eIVTCByteImage: { type::AronIVTCByteImagePtr casted = type::AronIVTCByteImagePtr::dynamicCast(aron); writer.writeIVTCByteImage(casted->width, casted->height, casted->typeName); break; } - case type::eOpenCVMat: + case type::Descriptor::eOpenCVMat: { type::AronOpenCVMatPtr casted = type::AronOpenCVMatPtr::dynamicCast(aron); writer.writeOpenCVMat(casted->dimensions, casted->typeName); break; } - case type::ePCLPointCloud: + case type::Descriptor::ePCLPointCloud: { type::AronPCLPointCloudPtr casted = type::AronPCLPointCloudPtr::dynamicCast(aron); writer.writePCLPointCloud(casted->width, casted->height, casted->typeName); break; } - case type::ePosition: + case type::Descriptor::ePosition: { writer.writePosition(); break; } - case type::eOrientation: + case type::Descriptor::eOrientation: { writer.writeOrientation(); break; } - case type::ePose: + case type::Descriptor::ePose: { writer.writePose(); break; } - case type::eInt: + case type::Descriptor::eInt: { type::AronIntPtr casted = type::AronIntPtr::dynamicCast(aron); writer.writeInt(); break; } - case type::eLong: + case type::Descriptor::eLong: { type::AronLongPtr casted = type::AronLongPtr::dynamicCast(aron); writer.writeLong(); break; } - case type::eFloat: + case type::Descriptor::eFloat: { type::AronFloatPtr casted = type::AronFloatPtr::dynamicCast(aron); writer.writeFloat(); break; } - case type::eDouble: + case type::Descriptor::eDouble: { type::AronDoublePtr casted = type::AronDoublePtr::dynamicCast(aron); writer.writeDouble(); break; } - case type::eString: + case type::Descriptor::eString: { type::AronStringPtr casted = type::AronStringPtr::dynamicCast(aron); writer.writeString(); break; } - case type::eBool: + case type::Descriptor::eBool: { type::AronBoolPtr casted = type::AronBoolPtr::dynamicCast(aron); writer.writeBool(); break; } - case type::eTime: + case type::Descriptor::eTime: { type::AronTimePtr casted = type::AronTimePtr::dynamicCast(aron); writer.writeTime(); @@ -171,7 +171,7 @@ namespace armarx::aron::typeIO } default: { - throw error::DescriptorNotValidException("LegacyAronTypeWriter", "SetupWriterFromAronTypePtr", "Type-Type could not be resolved. The ice_id of the input was: " + aron->ice_id(), desc); + throw error::DescriptorNotValidException("Visitor", "SetupWriterFromAronTypePtr", "Type-Type could not be resolved. The ice_id of the input was: " + aron->ice_id(), desc); } } } diff --git a/source/RobotAPI/libraries/aron/core/io/typeIO/visitor/Visitor.h b/source/RobotAPI/libraries/aron/core/io/typeIO/visitor/Visitor.h index 6f781b3dae61236e202ffffd0fd243f89732f5d7..fc9ea5b879011b109b5831418feab0e373311aef 100644 --- a/source/RobotAPI/libraries/aron/core/io/typeIO/visitor/Visitor.h +++ b/source/RobotAPI/libraries/aron/core/io/typeIO/visitor/Visitor.h @@ -41,8 +41,8 @@ namespace armarx::aron::typeIO Visitor() = delete; public: - static void SetupWriterFromAronTypePtr(WriterInterface&, const typenavigator::NavigatorPtr&); - static void SetupWriterFromAronTypePtr(WriterInterface&, const type::AronTypePtr&); + static void VisitAndSetup(WriterInterface&, const typenavigator::NavigatorPtr&); + static void VisitAndSetup(WriterInterface&, const type::AronTypePtr&); public: }; diff --git a/source/RobotAPI/libraries/aron/core/io/typeIO/writer/WriterToken.h b/source/RobotAPI/libraries/aron/core/io/typeIO/writer/WriterToken.h index 2b858da0c52b65d3e13d72b4ec3d11edc7ef7e4d..37be1d9cae29ffd46a84ab818fd3ac9f6967b705 100644 --- a/source/RobotAPI/libraries/aron/core/io/typeIO/writer/WriterToken.h +++ b/source/RobotAPI/libraries/aron/core/io/typeIO/writer/WriterToken.h @@ -86,7 +86,7 @@ namespace armarx::aron::typeIO protected: // members - type::Descriptor descriptor = type::eUnknown; + type::Descriptor descriptor = type::Descriptor::eUnknown; ElementTypename element; // current index diff --git a/source/RobotAPI/libraries/aron/core/io/typeIO/writer/navigator/NavigatorWriterToken.h b/source/RobotAPI/libraries/aron/core/io/typeIO/writer/navigator/NavigatorWriterToken.h index 20b337298c61c58e0665fb1bcf21bb54eb1d845d..d94350f9df9a19ef04898b70e34449c883062a95 100644 --- a/source/RobotAPI/libraries/aron/core/io/typeIO/writer/navigator/NavigatorWriterToken.h +++ b/source/RobotAPI/libraries/aron/core/io/typeIO/writer/navigator/NavigatorWriterToken.h @@ -56,32 +56,32 @@ namespace armarx::aron::typeIO::writer { switch (descriptor) { - case type::eDict: + case type::Descriptor::eDict: { typenavigator::DictNavigatorPtr casted = typenavigator::DictNavigator::DynamicCastAndCheck(element); casted->setAcceptedType(n); break; } - case type::eList: + case type::Descriptor::eList: { typenavigator::ListNavigatorPtr casted = typenavigator::ListNavigator::DynamicCastAndCheck(element); casted->setAcceptedType(n); break; } - case type::eObject: + case type::Descriptor::eObject: { typenavigator::ObjectNavigatorPtr casted = typenavigator::ObjectNavigator::DynamicCastAndCheck(element); casted->addMemberType(currentKey, n); break; } - case type::eTuple: + case type::Descriptor::eTuple: { typenavigator::TupleNavigatorPtr casted = typenavigator::TupleNavigator::DynamicCastAndCheck(element); casted->addAcceptedType(n); currentIndex++; break; } - case type::ePair: + case type::Descriptor::ePair: { typenavigator::PairNavigatorPtr casted = typenavigator::PairNavigator::DynamicCastAndCheck(element); casted->addAcceptedType(n); @@ -98,13 +98,13 @@ namespace armarx::aron::typeIO::writer { switch (descriptor) { - case type::eObject: + case type::Descriptor::eObject: { typenavigator::ObjectNavigatorPtr casted = typenavigator::ObjectNavigator::DynamicCast(element); casted->setObjectName(n); break; } - case type::eIntEnum: + case type::Descriptor::eIntEnum: { typenavigator::IntEnumNavigatorPtr casted = typenavigator::IntEnumNavigator::DynamicCast(element); casted->setEnumName(n); diff --git a/source/RobotAPI/libraries/aron/core/io/typeIO/writer/nlohmannJSON/NlohmannJSONWriter.cpp b/source/RobotAPI/libraries/aron/core/io/typeIO/writer/nlohmannJSON/NlohmannJSONWriter.cpp index 187c648096a0fa0e3c9e3b406b1dbc4a7f0b1dcf..0f3e96192baf5c2c5d088e0c3a5a2fb4e354d68d 100644 --- a/source/RobotAPI/libraries/aron/core/io/typeIO/writer/nlohmannJSON/NlohmannJSONWriter.cpp +++ b/source/RobotAPI/libraries/aron/core/io/typeIO/writer/nlohmannJSON/NlohmannJSONWriter.cpp @@ -30,7 +30,7 @@ namespace armarx::aron::typeIO::writer { nlohmann::json data; data[io::Data::READER_WRITER_NAME_SLUG] = n; - auto new_token = std::make_shared<NlohmannJSONWriterToken>(type::Descriptor::eList, data); + auto new_token = std::make_shared<NlohmannJSONWriterToken>(type::Descriptor::eObject, data); stack.push(new_token); } @@ -68,7 +68,7 @@ namespace armarx::aron::typeIO::writer void NlohmannJSONWriter::writeStartDict() { nlohmann::json data; - auto new_token = std::make_shared<NlohmannJSONWriterToken>(type::Descriptor::eList, data); + auto new_token = std::make_shared<NlohmannJSONWriterToken>(type::Descriptor::eDict, data); stack.push(new_token); } @@ -87,7 +87,7 @@ namespace armarx::aron::typeIO::writer void NlohmannJSONWriter::writeStartTuple() { nlohmann::json data; - auto new_token = std::make_shared<NlohmannJSONWriterToken>(type::Descriptor::eList, data); + auto new_token = std::make_shared<NlohmannJSONWriterToken>(type::Descriptor::eTuple, data); stack.push(new_token); } @@ -106,7 +106,7 @@ namespace armarx::aron::typeIO::writer void NlohmannJSONWriter::writeStartPair() { nlohmann::json data; - auto new_token = std::make_shared<NlohmannJSONWriterToken>(type::Descriptor::eList, data); + auto new_token = std::make_shared<NlohmannJSONWriterToken>(type::Descriptor::ePair, data); stack.push(new_token); } diff --git a/source/RobotAPI/libraries/aron/core/io/typeIO/writer/nlohmannJSON/NlohmannJSONWriterToken.h b/source/RobotAPI/libraries/aron/core/io/typeIO/writer/nlohmannJSON/NlohmannJSONWriterToken.h index 826524dddcd7c6a7d2e8bf7919240bb7d1b109b0..ea4410885b98ece7ee08e8c0ffb1c7443253c5f6 100644 --- a/source/RobotAPI/libraries/aron/core/io/typeIO/writer/nlohmannJSON/NlohmannJSONWriterToken.h +++ b/source/RobotAPI/libraries/aron/core/io/typeIO/writer/nlohmannJSON/NlohmannJSONWriterToken.h @@ -94,16 +94,5 @@ namespace armarx::aron::typeIO::writer } element[io::Data::READER_WRITER_NAME_SLUG] = n; } - - private: - // members - type::Descriptor descriptor; - nlohmann::json element; - - // current index - unsigned int currentIndex; - - // current key - std::string currentKey; }; } diff --git a/source/RobotAPI/libraries/aron/core/navigator/data/NavigatorFactory.cpp b/source/RobotAPI/libraries/aron/core/navigator/data/NavigatorFactory.cpp index 7f96d2392235838ba2348642aefb5fe0ac35e51c..d77251a9a47e5eca7f29eb38188f2617ebb1a40e 100644 --- a/source/RobotAPI/libraries/aron/core/navigator/data/NavigatorFactory.cpp +++ b/source/RobotAPI/libraries/aron/core/navigator/data/NavigatorFactory.cpp @@ -36,7 +36,7 @@ namespace armarx::aron::datanavigator NavigatorPtr NavigatorFactory::create(const data::AronDataPtr& aron, const Path& path) const { #define RUN_ARON_MACRO(upperType, lowerType, capsType) \ - {data::e##upperType, NavigatorFactoryPtr(new upperType##NavigatorFactory())}, + {data::Descriptor::e##upperType, NavigatorFactoryPtr(new upperType##NavigatorFactory())}, static const std::map<data::Descriptor, NavigatorFactoryPtr> Factories = { @@ -60,11 +60,11 @@ namespace armarx::aron::datanavigator // Factories #define RUN_ARON_MACRO(upperType, lowerType, capsType) \ -NavigatorPtr upperType##NavigatorFactory::createSpecific(const data::AronDataPtr& aron, const Path& path) const \ -{ \ -data::Aron##upperType##Ptr aronCasted = data::Aron##upperType##Ptr::dynamicCast(aron); \ -return datanavigator::NavigatorPtr(new upperType##Navigator(aronCasted, path)); \ -} + NavigatorPtr upperType##NavigatorFactory::createSpecific(const data::AronDataPtr& aron, const Path& path) const \ + { \ + data::Aron##upperType##Ptr aronCasted = data::Aron##upperType##Ptr::dynamicCast(aron); \ + return datanavigator::NavigatorPtr(new upperType##Navigator(aronCasted, path)); \ + } HANDLE_ALL_ARON_DATA #undef RUN_ARON_MACRO diff --git a/source/RobotAPI/libraries/aron/core/navigator/data/complex/NDArray.cpp b/source/RobotAPI/libraries/aron/core/navigator/data/complex/NDArray.cpp index a520f0140cec2013965a1f2517017033299ef05e..bdd6a0c20e87ed893627f3f75e7ffbde7b84b689 100644 --- a/source/RobotAPI/libraries/aron/core/navigator/data/complex/NDArray.cpp +++ b/source/RobotAPI/libraries/aron/core/navigator/data/complex/NDArray.cpp @@ -94,6 +94,10 @@ namespace armarx::aron::datanavigator bool NDArrayNavigator::equalsDeep(const NDArrayNavigatorPtr& other) const { + if (other == nullptr) + { + return false; + } return *this == *other; } @@ -205,14 +209,14 @@ namespace armarx::aron::datanavigator switch (type->getDescriptor()) { #define RUN_ARON_MACRO(upperType, lowerType, capsType) \ -case type::e##upperType: \ -{ \ -typenavigator::upperType##NavigatorPtr casted = typenavigator::upperType##Navigator::DynamicCast(type); \ -if (std::vector<int>(aron->dimensions.begin(), std::prev(aron->dimensions.end())) != casted->getDimensions() || aron->type != casted->getTypename()) \ +case type::Descriptor::e##upperType: \ { \ -return false; \ -} \ -break; \ + typenavigator::upperType##NavigatorPtr casted = typenavigator::upperType##Navigator::DynamicCast(type); \ + if (std::vector<int>(aron->dimensions.begin(), std::prev(aron->dimensions.end())) != casted->getDimensions() || aron->type != casted->getTypename()) \ + { \ + return false; \ + } \ + break; \ } HANDLE_NDARRAY_TYPES diff --git a/source/RobotAPI/libraries/aron/core/navigator/data/container/Dict.cpp b/source/RobotAPI/libraries/aron/core/navigator/data/container/Dict.cpp index 47c94a46ed0c90f49ecaadca8e534aa0c71b6374..67a2a6d816823611376158d2862c0b5918d6d693 100644 --- a/source/RobotAPI/libraries/aron/core/navigator/data/container/Dict.cpp +++ b/source/RobotAPI/libraries/aron/core/navigator/data/container/Dict.cpp @@ -30,267 +30,271 @@ #include <RobotAPI/libraries/aron/core/navigator/type/container/Object.h> namespace armarx::aron::datanavigator +{ + + // constructors + DictNavigator::DictNavigator(const Path& path) : + aron::Navigator<data::Descriptor, data::AronData>::Navigator(data::Descriptor::eDict, path), + Navigator(data::Descriptor::eDict, path), + aron(new data::AronDict()) + { + } + + DictNavigator::DictNavigator(const data::AronDictPtr& o, const Path& path) : + aron::Navigator<data::Descriptor, data::AronData>::Navigator(data::Descriptor::eDict, path), + Navigator(data::Descriptor::eDict, path), + aron(o) + { + CheckAronPtrForNull("DictNavigator", "DictNavigator", getPath(), aron); + + for (const auto& [key, dataPtr] : aron->elements) { - - // constructors - DictNavigator::DictNavigator(const Path& path) : - aron::Navigator<data::Descriptor, data::AronData>::Navigator(data::Descriptor::eDict, path), - Navigator(data::Descriptor::eDict, path), - aron(new data::AronDict()) - { - } - - DictNavigator::DictNavigator(const data::AronDictPtr& o, const Path& path) : - aron::Navigator<data::Descriptor, data::AronData>::Navigator(data::Descriptor::eDict, path), - Navigator(data::Descriptor::eDict, path), - aron(o) - { - CheckAronPtrForNull("DictNavigator", "DictNavigator", getPath(), aron); - - for (const auto& [key, dataPtr] : aron->elements) - { - childrenNavigators[key] = Navigator::FromAronData(dataPtr, Path(path, key)); - } - } - - DictNavigator::DictNavigator(const data::AronDataDict& d, const Path& path) : - DictNavigator(data::AronDictPtr(new data::AronDict(d)), path) - { - } - - DictNavigator::DictNavigator(const std::map<std::string, NavigatorPtr>& m, const Path& path) : - DictNavigator(path) - { - for (const auto& [key, dataPtr] : m) - { - addElement(key, dataPtr); - } - } - - // operators - bool DictNavigator::operator==(const DictNavigator& other) const - { - for (const auto& [key, nav] : childrenNavigators) - { - if (not(other.hasElement(key))) - { - return false; - } - if (not(nav->equalsDataNavigator(other.getElement(key)))) - { - return false; - } - } - return true; - } - - bool DictNavigator::equalsDataNavigator(const NavigatorPtr& other) const - { - if (other == nullptr) - { - return false; - } - DictNavigatorPtr casted = DynamicCast(other); - return equalsDeep(casted); - } - - bool DictNavigator::equalsDeep(const DictNavigatorPtr& other) const - { - return *this == *other; - } - - // static methods - DictNavigatorPtr DictNavigator::DynamicCast(const NavigatorPtr& n) - { - return std::dynamic_pointer_cast<DictNavigator>(n); - } - - DictNavigator DictNavigator::DynamicCast(Navigator& n) - { - return dynamic_cast<DictNavigator&>(n); - } - - DictNavigatorPtr DictNavigator::DynamicCastAndCheck(const NavigatorPtr& n) - { - CheckDataNavigatorPtrForNull("DictNavigator", "DynamicCastAndCheck[Before]", n); - DictNavigatorPtr casted = DictNavigator::DynamicCast(n); - CheckDataNavigatorPtrForNull("DictNavigator", "DynamicCastAndCheck[After]", n->getPath(), casted); - return casted; - } - - DictNavigatorPtr DictNavigator::FromAronDictPtr(const data::AronDictPtr& aron) - { - return std::make_shared<DictNavigator>(aron); - } - - data::AronDictPtr DictNavigator::ToAronDictPtr(const DictNavigatorPtr& navigator) - { - return navigator ? navigator->toAronDictPtr() : nullptr; - } - - data::AronDictPtr DictNavigator::toAronDictPtr() const - { - return aron; - } - - // public member functions - std::vector<std::string> DictNavigator::getAllKeys() const - { - std::vector<std::string> ret; - for (const auto& [key, _] : childrenNavigators) - { - ret.push_back(key); - } - return ret; - } - - void DictNavigator::addElement(const std::string& key, const NavigatorPtr& data) - { - this->childrenNavigators[key] = data; - this->aron->elements[key] = data->getResult(); - } - - bool DictNavigator::hasElement(const std::string& key) const + childrenNavigators[key] = Navigator::FromAronData(dataPtr, Path(path, key)); + } + } + + DictNavigator::DictNavigator(const data::AronDataDict& d, const Path& path) : + DictNavigator(data::AronDictPtr(new data::AronDict(d)), path) + { + } + + DictNavigator::DictNavigator(const std::map<std::string, NavigatorPtr>& m, const Path& path) : + DictNavigator(path) + { + for (const auto& [key, dataPtr] : m) + { + addElement(key, dataPtr); + } + } + + // operators + bool DictNavigator::operator==(const DictNavigator& other) const + { + for (const auto& [key, nav] : childrenNavigators) + { + if (not(other.hasElement(key))) { - return childrenNavigators.count(key) > 0; + return false; } - - NavigatorPtr DictNavigator::getElement(const std::string& key) const + if (not(nav->equalsDataNavigator(other.getElement(key)))) { - auto it = childrenNavigators.find(key); - if (it == childrenNavigators.end()) - { - std::string all_keys = ""; - for (const auto& child : this->getAllKeys()) - { - all_keys += child + ", "; - } - throw error::AronException("DictNavigator", "getElement", "Could not find key '" + key + "'. But I found the following keys: [" + all_keys + "]", getPath()); - } - return it->second; + return false; } + } + return true; + } - std::map<std::string, NavigatorPtr> DictNavigator::getElements() const + bool DictNavigator::equalsDataNavigator(const NavigatorPtr& other) const + { + if (other == nullptr) + { + return false; + } + DictNavigatorPtr casted = DynamicCast(other); + return equalsDeep(casted); + } + + bool DictNavigator::equalsDeep(const DictNavigatorPtr& other) const + { + if (other == nullptr) + { + return false; + } + return *this == *other; + } + + // static methods + DictNavigatorPtr DictNavigator::DynamicCast(const NavigatorPtr& n) + { + return std::dynamic_pointer_cast<DictNavigator>(n); + } + + DictNavigator DictNavigator::DynamicCast(Navigator& n) + { + return dynamic_cast<DictNavigator&>(n); + } + + DictNavigatorPtr DictNavigator::DynamicCastAndCheck(const NavigatorPtr& n) + { + CheckDataNavigatorPtrForNull("DictNavigator", "DynamicCastAndCheck[Before]", n); + DictNavigatorPtr casted = DictNavigator::DynamicCast(n); + CheckDataNavigatorPtrForNull("DictNavigator", "DynamicCastAndCheck[After]", n->getPath(), casted); + return casted; + } + + DictNavigatorPtr DictNavigator::FromAronDictPtr(const data::AronDictPtr& aron) + { + return std::make_shared<DictNavigator>(aron); + } + + data::AronDictPtr DictNavigator::ToAronDictPtr(const DictNavigatorPtr& navigator) + { + return navigator ? navigator->toAronDictPtr() : nullptr; + } + + data::AronDictPtr DictNavigator::toAronDictPtr() const + { + return aron; + } + + // public member functions + std::vector<std::string> DictNavigator::getAllKeys() const + { + std::vector<std::string> ret; + for (const auto& [key, _] : childrenNavigators) + { + ret.push_back(key); + } + return ret; + } + + void DictNavigator::addElement(const std::string& key, const NavigatorPtr& data) + { + this->childrenNavigators[key] = data; + this->aron->elements[key] = data->getResult(); + } + + bool DictNavigator::hasElement(const std::string& key) const + { + return childrenNavigators.count(key) > 0; + } + + NavigatorPtr DictNavigator::getElement(const std::string& key) const + { + auto it = childrenNavigators.find(key); + if (it == childrenNavigators.end()) + { + std::string all_keys = ""; + for (const auto& child : this->getAllKeys()) { - return childrenNavigators; + all_keys += child + ", "; } - - void DictNavigator::clear() + throw error::AronException("DictNavigator", "getElement", "Could not find key '" + key + "'. But I found the following keys: [" + all_keys + "]", getPath()); + } + return it->second; + } + + std::map<std::string, NavigatorPtr> DictNavigator::getElements() const + { + return childrenNavigators; + } + + void DictNavigator::clear() + { + childrenNavigators.clear(); + aron->elements.clear(); + } + + // virtual implementations + data::AronDataPtr DictNavigator::getResult() const + { + return toAronDictPtr(); + } + + std::string DictNavigator::getName() const + { + return "AronDict"; + } + + typenavigator::NavigatorPtr DictNavigator::recalculateType() const + { + typenavigator::DictNavigatorPtr typenav = typenavigator::DictNavigatorPtr(new typenavigator::DictNavigator(getPath())); + for (const auto& [key, nav] : childrenNavigators) + { + if (typenav->getAcceptedType() == nullptr) { - childrenNavigators.clear(); - aron->elements.clear(); + typenav->setAcceptedType(nav->recalculateType()); + continue; } - // virtual implementations - data::AronDataPtr DictNavigator::getResult() const + if (!nav->fullfillsType(typenav->getAcceptedType())) { - return toAronDictPtr(); + throw error::AronException("DictNavigator", "recalculateType", "Cannot recalculate the aronType. Inconsistency found for key: " + key, getPath()); } + } + return typenav->getAcceptedType(); + } - std::string DictNavigator::getName() const - { - return "AronDict"; - } + bool DictNavigator::fullfillsType(const typenavigator::NavigatorPtr& type) const + { + if (!Resolver::Correspond(type->getDescriptor(), getDescriptor())) + { + return false; + } - typenavigator::NavigatorPtr DictNavigator::recalculateType() const + type::Descriptor typeDesc = type->getDescriptor(); + switch (typeDesc) + { + case type::Descriptor::eObject: { - typenavigator::DictNavigatorPtr typenav = typenavigator::DictNavigatorPtr(new typenavigator::DictNavigator(getPath())); + typenavigator::ObjectNavigatorPtr objectTypeNav = typenavigator::ObjectNavigator::DynamicCast(type); for (const auto& [key, nav] : childrenNavigators) { - if (typenav->getAcceptedType() == nullptr) - { - typenav->setAcceptedType(nav->recalculateType()); - continue; - } - - if (!nav->fullfillsType(typenav->getAcceptedType())) + if (!nav->fullfillsType(objectTypeNav->getMemberType(key))) { - throw error::AronException("DictNavigator", "recalculateType", "Cannot recalculate the aronType. Inconsistency found for key: " + key, getPath()); + return false; } } - return typenav->getAcceptedType(); + return true; } - - bool DictNavigator::fullfillsType(const typenavigator::NavigatorPtr& type) const + case type::Descriptor::eDict: { - if (!Resolver::Correspond(type->getDescriptor(), getDescriptor())) - { - return false; - } - - type::Descriptor typeDesc = type->getDescriptor(); - switch(typeDesc) - { - case type::eObject: - { - typenavigator::ObjectNavigatorPtr objectTypeNav = typenavigator::ObjectNavigator::DynamicCast(type); - for (const auto& [key, nav] : childrenNavigators) - { - if (!nav->fullfillsType(objectTypeNav->getMemberType(key))) - { - return false; - } - } - return true; - } - case type::eDict: + typenavigator::DictNavigatorPtr dictTypeNav = typenavigator::DictNavigator::DynamicCast(type); + for (const auto& [_, nav] : childrenNavigators) { - typenavigator::DictNavigatorPtr dictTypeNav = typenavigator::DictNavigator::DynamicCast(type); - for (const auto& [_, nav] : childrenNavigators) + if (!nav->fullfillsType(dictTypeNav->getAcceptedType())) { - if (!nav->fullfillsType(dictTypeNav->getAcceptedType())) - { - return false; - } + return false; } - return true; - } - default: - return false; - } - } - - std::vector<NavigatorPtr> DictNavigator::getChildren() const - { - std::vector<NavigatorPtr> ret(childrenNavigators.size()); - for (const auto& [key, nav] : childrenNavigators) - { - ret.push_back(nav); - } - return ret; - } - - size_t DictNavigator::childrenSize() const - { - return childrenNavigators.size(); - } - - NavigatorPtr DictNavigator::navigateAbsolute(const Path& path) const - { - if (!path.hasElement()) - { - throw error::AronException("DictNavigator", "navigate", "Could not navigate without a valid path. The path was empty."); - } - std::string el = path.getFirstElement(); - if (!hasElement(el)) - { - throw error::StringNotValidException("DictNavigator", "navigate", "Could not find an element of a path.", el); - } - - if (path.size() == 1) - { - return childrenNavigators.at(el); - } - else - { - Path next = path.withDetachedFirstElement(); - return childrenNavigators.at(el)->navigateAbsolute(next); } + return true; } + default: + return false; + } + } + + std::vector<NavigatorPtr> DictNavigator::getChildren() const + { + std::vector<NavigatorPtr> ret(childrenNavigators.size()); + for (const auto& [key, nav] : childrenNavigators) + { + ret.push_back(nav); + } + return ret; + } + + size_t DictNavigator::childrenSize() const + { + return childrenNavigators.size(); + } + + NavigatorPtr DictNavigator::navigateAbsolute(const Path& path) const + { + if (!path.hasElement()) + { + throw error::AronException("DictNavigator", "navigate", "Could not navigate without a valid path. The path was empty."); + } + std::string el = path.getFirstElement(); + if (!hasElement(el)) + { + throw error::StringNotValidException("DictNavigator", "navigate", "Could not find an element of a path.", el); + } - NavigatorPtr DictNavigator::navigateRelative(const Path& path) const - { - Path absoluteFromHere = path.getWithoutPrefix(getPath()); - return navigateAbsolute(absoluteFromHere); - } + if (path.size() == 1) + { + return childrenNavigators.at(el); + } + else + { + Path next = path.withDetachedFirstElement(); + return childrenNavigators.at(el)->navigateAbsolute(next); + } + } + + NavigatorPtr DictNavigator::navigateRelative(const Path& path) const + { + Path absoluteFromHere = path.getWithoutPrefix(getPath()); + return navigateAbsolute(absoluteFromHere); + } } diff --git a/source/RobotAPI/libraries/aron/core/navigator/data/container/List.cpp b/source/RobotAPI/libraries/aron/core/navigator/data/container/List.cpp index e9c546a460d12248ecef198c2f25369e803fd0ec..d2d5bee4af83060dad86c93498be761f42a84f80 100644 --- a/source/RobotAPI/libraries/aron/core/navigator/data/container/List.cpp +++ b/source/RobotAPI/libraries/aron/core/navigator/data/container/List.cpp @@ -32,261 +32,265 @@ #include <RobotAPI/libraries/aron/core/navigator/type/container/Pair.h> namespace armarx::aron::datanavigator +{ + // constructors + ListNavigator::ListNavigator(const Path& path) : + aron::Navigator<data::Descriptor, data::AronData>::Navigator(data::Descriptor::eList, path), + Navigator(data::Descriptor::eList, path), + aron(new data::AronList()) + { + } + + ListNavigator::ListNavigator(const data::AronListPtr& l, const Path& path) : + aron::Navigator<data::Descriptor, data::AronData>::Navigator(data::Descriptor::eList, path), + Navigator(data::Descriptor::eList, path), + aron(l) + { + CheckAronPtrForNull("ListNavigator", "ListNavigator", getPath(), aron); + + unsigned int i = 0; + for (const auto& dataPtr : l->elements) { - // constructors - ListNavigator::ListNavigator(const Path& path) : - aron::Navigator<data::Descriptor, data::AronData>::Navigator(data::Descriptor::eList, path), - Navigator(data::Descriptor::eList, path), - aron(new data::AronList()) + childrenNavigators.push_back(FromAronData(dataPtr, Path(path, std::to_string(i++)))); + } + } + + ListNavigator::ListNavigator(const data::AronDataList& d, const Path& path) : + ListNavigator(data::AronListPtr(new data::AronList(d)), path) + { + } + + ListNavigator::ListNavigator(const std::vector<NavigatorPtr>& n, const Path& path) : + ListNavigator(path) + { + for (const auto& dataPtr : n) + { + addElement(dataPtr); + } + } + + // operators + bool ListNavigator::operator==(const ListNavigator& other) const + { + unsigned int i = 0; + for (const auto& nav : childrenNavigators) + { + if (not(other.hasElement(i))) { + return false; } - - ListNavigator::ListNavigator(const data::AronListPtr& l, const Path& path) : - aron::Navigator<data::Descriptor, data::AronData>::Navigator(data::Descriptor::eList, path), - Navigator(data::Descriptor::eList, path), - aron(l) + if (not(nav->equalsDataNavigator(other.getElement(i)))) { - CheckAronPtrForNull("ListNavigator", "ListNavigator", getPath(), aron); - - unsigned int i = 0; - for (const auto& dataPtr : l->elements) - { - childrenNavigators.push_back(FromAronData(dataPtr, Path(path, std::to_string(i++)))); - } + return false; } - - ListNavigator::ListNavigator(const data::AronDataList& d, const Path& path) : - ListNavigator(data::AronListPtr(new data::AronList(d)), path) + i++; + } + return true; + } + + bool ListNavigator::equalsDataNavigator(const NavigatorPtr& other) const + { + if (other == nullptr) + { + return false; + } + ListNavigatorPtr casted = DynamicCast(other); + return equalsDeep(casted); + } + + bool ListNavigator::equalsDeep(const ListNavigatorPtr& other) const + { + if (other == nullptr) + { + return false; + } + return *this == *other; + } + + // static methods + ListNavigatorPtr ListNavigator::DynamicCast(const NavigatorPtr& n) + { + ListNavigatorPtr casted = std::dynamic_pointer_cast<ListNavigator>(n); + return casted; + } + + ListNavigator ListNavigator::DynamicCast(Navigator& n) + { + return dynamic_cast<ListNavigator&>(n); + } + + ListNavigatorPtr ListNavigator::DynamicCastAndCheck(const NavigatorPtr& n) + { + CheckDataNavigatorPtrForNull("ListNavigator", "DynamicCastAndCheck[Before]", n); + ListNavigatorPtr casted = ListNavigator::DynamicCast(n); + CheckDataNavigatorPtrForNull("ListNavigator", "DynamicCastAndCheck[After]", n->getPath(), casted); + return casted; + } + + ListNavigatorPtr ListNavigator::FromAronListPtr(const data::AronListPtr& aron) + { + return std::make_shared<ListNavigator>(aron); + } + + data::AronListPtr ListNavigator::ToAronListPtr(const ListNavigatorPtr& navigator) + { + return navigator ? navigator->toAronListPtr() : nullptr; + } + + // public member functions + void ListNavigator::addElement(const NavigatorPtr& n) + { + childrenNavigators.push_back(n); + aron->elements.push_back(n->getResult()); + } + + bool ListNavigator::hasElement(unsigned int i) const + { + return i < childrenNavigators.size(); + } + + NavigatorPtr ListNavigator::getElement(unsigned int i) const + { + if (i >= childrenNavigators.size()) + { + throw error::AronException("ListNavigator", "getElement", "The index i = " + std::to_string(i) + " is out of bounds (size = " + std::to_string(childrenNavigators.size()) + ")", getPath()); + } + return childrenNavigators[i]; + } + + std::vector<NavigatorPtr> ListNavigator::getElements() const + { + return childrenNavigators; + } + + void ListNavigator::clear() + { + childrenNavigators.clear(); + aron->elements.clear(); + } + + data::AronListPtr ListNavigator::toAronListPtr() const + { + return aron; + } + + // virtual implementations + data::AronDataPtr ListNavigator::getResult() const + { + return toAronListPtr(); + } + + std::string ListNavigator::getName() const + { + return "AronList"; + } + + typenavigator::NavigatorPtr ListNavigator::recalculateType() const + { + typenavigator::ListNavigatorPtr typenav = typenavigator::ListNavigatorPtr(new typenavigator::ListNavigator(getPath())); + unsigned int i = 0; + for (const auto& nav : childrenNavigators) + { + if (typenav->getAcceptedType() == nullptr) { + typenav->setAcceptedType(nav->recalculateType()); + continue; } - ListNavigator::ListNavigator(const std::vector<NavigatorPtr>& n, const Path& path) : - ListNavigator(path) + if (!nav->fullfillsType(typenav->getAcceptedType())) { - for (const auto& dataPtr : n) - { - addElement(dataPtr); - } + throw error::AronException("ListNavigator", "recalculateType", "Cannot recalculate the aronType. Inconsistency found for index: " + std::to_string(i), getPath()); } + ++i; + } + return typenav->getAcceptedType(); + } + + bool ListNavigator::fullfillsType(const typenavigator::NavigatorPtr& type) const + { + if (!Resolver::Correspond(type->getDescriptor(), getDescriptor())) + { + return false; + } - // operators - bool ListNavigator::operator==(const ListNavigator& other) const + type::Descriptor typeDesc = type->getDescriptor(); + switch (typeDesc) + { + case type::Descriptor::eList: { - unsigned int i = 0; + typenavigator::ListNavigatorPtr listTypeNav = typenavigator::ListNavigator::DynamicCast(type); for (const auto& nav : childrenNavigators) { - if (not(other.hasElement(i))) - { - return false; - } - if (not(nav->equalsDataNavigator(other.getElement(i)))) + if (!nav->fullfillsType(listTypeNav->getAcceptedType())) { return false; } - i++; } return true; } - - bool ListNavigator::equalsDataNavigator(const NavigatorPtr& other) const - { - if (other == nullptr) - { - return false; - } - ListNavigatorPtr casted = DynamicCast(other); - return equalsDeep(casted); - } - - bool ListNavigator::equalsDeep(const ListNavigatorPtr& other) const - { - return *this == *other; - } - - // static methods - ListNavigatorPtr ListNavigator::DynamicCast(const NavigatorPtr& n) - { - ListNavigatorPtr casted = std::dynamic_pointer_cast<ListNavigator>(n); - return casted; - } - - ListNavigator ListNavigator::DynamicCast(Navigator& n) - { - return dynamic_cast<ListNavigator&>(n); - } - - ListNavigatorPtr ListNavigator::DynamicCastAndCheck(const NavigatorPtr& n) - { - CheckDataNavigatorPtrForNull("ListNavigator", "DynamicCastAndCheck[Before]", n); - ListNavigatorPtr casted = ListNavigator::DynamicCast(n); - CheckDataNavigatorPtrForNull("ListNavigator", "DynamicCastAndCheck[After]", n->getPath(), casted); - return casted; - } - - ListNavigatorPtr ListNavigator::FromAronListPtr(const data::AronListPtr& aron) - { - return std::make_shared<ListNavigator>(aron); - } - - data::AronListPtr ListNavigator::ToAronListPtr(const ListNavigatorPtr& navigator) - { - return navigator ? navigator->toAronListPtr() : nullptr; - } - - // public member functions - void ListNavigator::addElement(const NavigatorPtr& n) - { - childrenNavigators.push_back(n); - aron->elements.push_back(n->getResult()); - } - - bool ListNavigator::hasElement(unsigned int i) const - { - return i < childrenNavigators.size(); - } - - NavigatorPtr ListNavigator::getElement(unsigned int i) const - { - if (i >= childrenNavigators.size()) - { - throw error::AronException("ListNavigator", "getElement", "The index i = " + std::to_string(i) + " is out of bounds (size = " + std::to_string(childrenNavigators.size()) + ")", getPath()); - } - return childrenNavigators[i]; - } - - std::vector<NavigatorPtr> ListNavigator::getElements() const - { - return childrenNavigators; - } - - void ListNavigator::clear() - { - childrenNavigators.clear(); - aron->elements.clear(); - } - - data::AronListPtr ListNavigator::toAronListPtr() const - { - return aron; - } - - // virtual implementations - data::AronDataPtr ListNavigator::getResult() const + case type::Descriptor::eTuple: { - return toAronListPtr(); - } - - std::string ListNavigator::getName() const - { - return "AronList"; - } - - typenavigator::NavigatorPtr ListNavigator::recalculateType() const - { - typenavigator::ListNavigatorPtr typenav = typenavigator::ListNavigatorPtr(new typenavigator::ListNavigator(getPath())); + typenavigator::TupleNavigatorPtr tupleTypeNav = typenavigator::TupleNavigator::DynamicCast(type); unsigned int i = 0; for (const auto& nav : childrenNavigators) { - if (typenav->getAcceptedType() == nullptr) - { - typenav->setAcceptedType(nav->recalculateType()); - continue; - } - - if (!nav->fullfillsType(typenav->getAcceptedType())) - { - throw error::AronException("ListNavigator", "recalculateType", "Cannot recalculate the aronType. Inconsistency found for index: " + std::to_string(i), getPath()); - } - ++i; - } - return typenav->getAcceptedType(); - } - - bool ListNavigator::fullfillsType(const typenavigator::NavigatorPtr& type) const - { - if (!Resolver::Correspond(type->getDescriptor(), getDescriptor())) - { - return false; - } - - type::Descriptor typeDesc = type->getDescriptor(); - switch(typeDesc) - { - case type::eList: - { - typenavigator::ListNavigatorPtr listTypeNav = typenavigator::ListNavigator::DynamicCast(type); - for (const auto& nav : childrenNavigators) - { - if (!nav->fullfillsType(listTypeNav->getAcceptedType())) - { - return false; - } - } - return true; - } - case type::eTuple: - { - typenavigator::TupleNavigatorPtr tupleTypeNav = typenavigator::TupleNavigator::DynamicCast(type); - unsigned int i = 0; - for (const auto& nav : childrenNavigators) - { - if (!nav->fullfillsType(tupleTypeNav->getAcceptedType(i))) - { - return false; - } - } - return true; - } - case type::ePair: - { - typenavigator::PairNavigatorPtr pairTypeNav = typenavigator::PairNavigator::DynamicCast(type); - if(childrenSize() != 2) + if (!nav->fullfillsType(tupleTypeNav->getAcceptedType(i))) { return false; } - return childrenNavigators[0]->fullfillsType(pairTypeNav->getFirstAcceptedType()) && childrenNavigators[1]->fullfillsType(pairTypeNav->getSecondAcceptedType()); - } - default: - return false; } + return true; } - - std::vector<NavigatorPtr> ListNavigator::getChildren() const - { - return childrenNavigators; - } - - size_t ListNavigator::childrenSize() const - { - return childrenNavigators.size(); - } - - NavigatorPtr ListNavigator::navigateAbsolute(const Path& path) const + case type::Descriptor::ePair: { - if (!path.hasElement()) + typenavigator::PairNavigatorPtr pairTypeNav = typenavigator::PairNavigator::DynamicCast(type); + if (childrenSize() != 2) { - throw error::AronException("ListNavigator", "navigate", "Could not navigate without a valid path. The path was empty."); - } - unsigned int i = std::stoi(path.getFirstElement()); - if (!hasElement(i)) - { - throw error::IndexNotValidException("ListNavigator", "navigate", "Could not find an element of a path.", i, childrenSize()); - } - - if (path.size() == 1) - { - return childrenNavigators.at(i); - } - else - { - Path next = path.withDetachedFirstElement(); - return childrenNavigators.at(i)->navigateAbsolute(next); + return false; } + return childrenNavigators[0]->fullfillsType(pairTypeNav->getFirstAcceptedType()) && childrenNavigators[1]->fullfillsType(pairTypeNav->getSecondAcceptedType()); } + default: + return false; + } + } + + std::vector<NavigatorPtr> ListNavigator::getChildren() const + { + return childrenNavigators; + } + + size_t ListNavigator::childrenSize() const + { + return childrenNavigators.size(); + } + + NavigatorPtr ListNavigator::navigateAbsolute(const Path& path) const + { + if (!path.hasElement()) + { + throw error::AronException("ListNavigator", "navigate", "Could not navigate without a valid path. The path was empty."); + } + unsigned int i = std::stoi(path.getFirstElement()); + if (!hasElement(i)) + { + throw error::IndexNotValidException("ListNavigator", "navigate", "Could not find an element of a path.", i, childrenSize()); + } - NavigatorPtr ListNavigator::navigateRelative(const Path& path) const - { - Path absoluteFromHere = path.getWithoutPrefix(getPath()); - return navigateAbsolute(absoluteFromHere); - } + if (path.size() == 1) + { + return childrenNavigators.at(i); + } + else + { + Path next = path.withDetachedFirstElement(); + return childrenNavigators.at(i)->navigateAbsolute(next); + } + } + + NavigatorPtr ListNavigator::navigateRelative(const Path& path) const + { + Path absoluteFromHere = path.getWithoutPrefix(getPath()); + return navigateAbsolute(absoluteFromHere); + } } diff --git a/source/RobotAPI/libraries/aron/core/navigator/data/primitive/Primitive.cpp b/source/RobotAPI/libraries/aron/core/navigator/data/primitive/Primitive.cpp index c5b3ea636c67aee8261abedba5099ba3a8f927ea..23e117fc3f23ed1639faa0b310ba9ddd0f997e24 100644 --- a/source/RobotAPI/libraries/aron/core/navigator/data/primitive/Primitive.cpp +++ b/source/RobotAPI/libraries/aron/core/navigator/data/primitive/Primitive.cpp @@ -27,7 +27,7 @@ #include <RobotAPI/libraries/aron/core/navigator/type/primitive/Primitive.h> namespace armarx::aron::datanavigator - { +{ #define RUN_ARON_MACRO(upperType, lowerType, capsType) \ /* constructors */ \ upperType##Navigator::upperType##Navigator(const data::Aron##upperType##Ptr& o, const Path& path) : \ @@ -50,6 +50,11 @@ namespace armarx::aron::datanavigator } \ \ /* operators */ \ + upperType##Navigator::operator lowerType() const \ + { \ + return aron->value; \ + } \ + \ bool upperType##Navigator::operator==(const upperType##Navigator& other) const \ { \ const auto& otherAron = other.toAron##upperType##Ptr(); \ @@ -71,6 +76,10 @@ namespace armarx::aron::datanavigator bool upperType##Navigator::equalsDeep(const upperType##NavigatorPtr& other) const \ { \ /* only for consistency. There is no "deep" comparison. */ \ + if (other == nullptr) \ + { \ + return false; \ + } \ return *this == *other; \ } \ \ @@ -151,6 +160,6 @@ namespace armarx::aron::datanavigator return 0; \ } \ - HANDLE_PRIMITIVE_DATA + HANDLE_PRIMITIVE_DATA #undef RUN_ARON_MACRO } diff --git a/source/RobotAPI/libraries/aron/core/navigator/data/primitive/Primitive.h b/source/RobotAPI/libraries/aron/core/navigator/data/primitive/Primitive.h index 195887d017be92fdd3cbeb36729d9c507834ef94..2891a277fd1e2d13f116bce302957bcc6042f746 100644 --- a/source/RobotAPI/libraries/aron/core/navigator/data/primitive/Primitive.h +++ b/source/RobotAPI/libraries/aron/core/navigator/data/primitive/Primitive.h @@ -37,7 +37,7 @@ namespace armarx::aron::datanavigator class upperType##Navigator; \ typedef std::shared_ptr<upperType##Navigator> upperType##NavigatorPtr; - HANDLE_PRIMITIVE_DATA + HANDLE_PRIMITIVE_DATA #undef RUN_ARON_MACRO @@ -54,6 +54,7 @@ namespace armarx::aron::datanavigator upperType##Navigator(const lowerType&, const Path& = Path()); \ \ /* operators */ \ + operator lowerType() const; \ bool operator==(const upperType##Navigator&) const; \ virtual bool equalsDataNavigator(const NavigatorPtr&) const override; \ bool equalsDeep(const upperType##NavigatorPtr&) const; \ @@ -86,6 +87,6 @@ namespace armarx::aron::datanavigator data::Aron##upperType##Ptr aron; \ }; - HANDLE_PRIMITIVE_DATA + HANDLE_PRIMITIVE_DATA #undef RUN_ARON_MACRO } diff --git a/source/RobotAPI/libraries/aron/core/navigator/type/NavigatorFactory.cpp b/source/RobotAPI/libraries/aron/core/navigator/type/NavigatorFactory.cpp index 83b72bf347b46624161b4e2133a049e261d09965..d227f5e1e09b87e362be3c1baf9280fac46123e5 100644 --- a/source/RobotAPI/libraries/aron/core/navigator/type/NavigatorFactory.cpp +++ b/source/RobotAPI/libraries/aron/core/navigator/type/NavigatorFactory.cpp @@ -35,7 +35,7 @@ namespace armarx::aron::typenavigator NavigatorPtr NavigatorFactory::create(const type::AronTypePtr& aron, const Path& path) const { #define RUN_ARON_MACRO(upperType, lowerType, capsType) \ - {type::e##upperType, NavigatorFactoryPtr(new upperType##NavigatorFactory())}, + {type::Descriptor::e##upperType, NavigatorFactoryPtr(new upperType##NavigatorFactory())}, static const std::map<type::Descriptor, NavigatorFactoryPtr> Factories = { @@ -59,11 +59,11 @@ namespace armarx::aron::typenavigator // Factories #define RUN_ARON_MACRO(upperType, lowerType, capsType) \ -NavigatorPtr upperType##NavigatorFactory::createSpecific(const type::AronTypePtr& aron, const Path& path) const \ -{ \ -type::Aron##upperType##Ptr aronCasted = type::Aron##upperType##Ptr::dynamicCast(aron); \ -return typenavigator::NavigatorPtr(new upperType##Navigator(aronCasted, path)); \ -} + NavigatorPtr upperType##NavigatorFactory::createSpecific(const type::AronTypePtr& aron, const Path& path) const \ + { \ + type::Aron##upperType##Ptr aronCasted = type::Aron##upperType##Ptr::dynamicCast(aron); \ + return typenavigator::NavigatorPtr(new upperType##Navigator(aronCasted, path)); \ + } HANDLE_ALL_ARON_TYPES #undef RUN_ARON_MACRO diff --git a/source/RobotAPI/libraries/aron/core/navigator/type/container/Object.cpp b/source/RobotAPI/libraries/aron/core/navigator/type/container/Object.cpp index 8f82d1d0776d9b4629f6a75379b56f70661e9531..bc030f335ae8d67ecd9160e949a8943d99196e16 100644 --- a/source/RobotAPI/libraries/aron/core/navigator/type/container/Object.cpp +++ b/source/RobotAPI/libraries/aron/core/navigator/type/container/Object.cpp @@ -24,6 +24,9 @@ // Header #include "Object.h" +// ArmarX +#include "SimoxUtility/algorithm/get_map_keys_values.h" + namespace armarx::aron::typenavigator { @@ -88,6 +91,10 @@ namespace armarx::aron::typenavigator NavigatorPtr ObjectNavigator::getMemberType(const std::string& s) const { + if (memberTypes.find(s) == memberTypes.end()) + { + throw error::StringNotValidException("ObjectNavigator", "getMemberType", "Member not set. The list of all members is: " + simox::alg::to_string(simox::alg::get_keys(memberTypes)), s); + } return memberTypes.at(s); } diff --git a/source/RobotAPI/libraries/aron/core/test/aronTest.cpp b/source/RobotAPI/libraries/aron/core/test/aronTest.cpp index 1210ed0a5d0058825dede94196653f0af3fc201f..e8fd551be59727494f1c92040d81a8bddf1fe8bd 100644 --- a/source/RobotAPI/libraries/aron/core/test/aronTest.cpp +++ b/source/RobotAPI/libraries/aron/core/test/aronTest.cpp @@ -154,7 +154,7 @@ void runTestWithInstances(T& k1, T& k2) std::string k1_aron_json_str = k1_aron_json.dump(4); armarx::aron::dataIO::writer::NlohmannJSONWriter direct_json_writer_for_k1; - armarx::aron::dataIO::Visitor::SetupWriterFromAronDataPtr(direct_json_writer_for_k1, k1_aron); + armarx::aron::dataIO::Visitor::VisitAndSetup(direct_json_writer_for_k1, k1_aron); nlohmann::json direct_k1_aron_json = direct_json_writer_for_k1.getResult(); std::string direct_k1_aron_json_str = direct_k1_aron_json.dump(4); BOOST_CHECK_EQUAL((k1_aron_json_str == direct_k1_aron_json_str), true);