Index: src/libserializer/SerializableContainer.h =================================================================== diff -u -N -r08717141ce5f6926116c298cbc9442094a45bb67 -re9d12da97d434708c93b6967971ce265ac933252 --- src/libserializer/SerializableContainer.h (.../SerializableContainer.h) (revision 08717141ce5f6926116c298cbc9442094a45bb67) +++ src/libserializer/SerializableContainer.h (.../SerializableContainer.h) (revision e9d12da97d434708c93b6967971ce265ac933252) @@ -1,14 +1,46 @@ #pragma once +#include "../libchcore/TCoreException.h" +#include "../libchcore/ErrorCodes.h" namespace serializer { template class SerializableContainer { public: + SerializableContainer() = default; + SerializableContainer(const SerializableContainer& rSrc) + { + for(const T& item : rSrc.m_vEntries) + { + // ensures proper assignment of new oids + Add(item); + } + } + + SerializableContainer& operator=(const SerializableContainer& rSrc) + { + if(this != &rSrc) + { + Clear(); + for(const T& item : rSrc.m_vEntries) + { + // ensures proper assignment of new oids + Add(item); + } + } + + return *this; + } + + virtual ~SerializableContainer() = default; + void Store(const serializer::ISerializerContainerPtr& spContainer) const { + if(!spContainer) + throw chcore::TCoreException(chcore::eErr_InvalidPointer, L"spContainer", LOCATION); + InitColumns(spContainer); spContainer->DeleteRows(m_setRemovedObjects); @@ -22,6 +54,12 @@ void Load(const serializer::ISerializerContainerPtr& spContainer) { + if(!spContainer) + throw chcore::TCoreException(chcore::eErr_InvalidPointer, L"spContainer", LOCATION); + + m_setRemovedObjects.Clear(); + m_vEntries.clear(); + InitColumns(spContainer); ISerializerRowReaderPtr spRowReader = spContainer->GetRowReader(); @@ -30,10 +68,15 @@ T tEntry; tEntry.Load(spRowReader); - tEntry.ResetModifications(); - m_vEntries.push_back(tEntry); } + + // ensure all objects have modification flag stripped to avoid unnecessary writing the same data to db again + // NOTE: Load() method above should reset modification flag, but storing it in vector will set it again - hence the separate reset + for(T& rItem : m_vEntries) + { + rItem.ResetModifications(); + } } virtual void InitColumns(const serializer::ISerializerContainerPtr& spContainer) const = 0; @@ -45,7 +88,8 @@ void Add(const T& rEntry) { - m_vEntries.push_back(rEntry); + auto iterResult = m_vEntries.insert(m_vEntries.end(), rEntry); + iterResult->SetObjectID(++m_oidLastObjectID); } bool SetAt(size_t stIndex, const T& rNewEntry) @@ -55,6 +99,7 @@ { T& rEntry = m_vEntries.at(stIndex); + // set only data, without changing oid rEntry.SetData(rNewEntry); return true; } @@ -67,7 +112,8 @@ BOOST_ASSERT(stIndex <= m_vEntries.size()); if(stIndex <= m_vEntries.size()) { - m_vEntries.insert(m_vEntries.begin() + stIndex, rNewEntry); + auto iterResult = m_vEntries.insert(m_vEntries.begin() + stIndex, rNewEntry); + iterResult->SetObjectID(++m_oidLastObjectID); return true; } @@ -119,6 +165,7 @@ } protected: + serializer::object_id_t m_oidLastObjectID = 0; std::vector m_vEntries; mutable serializer::TRemovedObjects m_setRemovedObjects; };