[commit] r2713 - in trunk: Doc GME/Mga Tests/GPyUnit
GMESRC Repository Notifications
gme-commit at list.isis.vanderbilt.edu
Fri Nov 10 16:01:54 CST 2017
Author: ksmyth
Date: Fri Nov 10 16:01:54 2017
New Revision: 2713
Log:
DetachFromArchetype: fix bug where attribute values from basetype's basetype were lost
Modified:
trunk/Doc/README_in.txt
trunk/GME/Mga/MgaComplexOps.cpp
trunk/Tests/GPyUnit/test_instances.py
Modified: trunk/Doc/README_in.txt
==============================================================================
--- trunk/Doc/README_in.txt Fri Nov 10 16:01:50 2017 (r2712)
+++ trunk/Doc/README_in.txt Fri Nov 10 16:01:54 2017 (r2713)
@@ -30,6 +30,7 @@
- Binary compatibility with 11.12.2
- Fix crash under GME x64 and high memory usage
- IMgaProject.ObjectByID fail when there is not object with the supplied ID
+ - DetachFromArchetype: fix bug where attribute values from basetype's basetype were lost
Release Notes of Release 17.10.13
----------------------------------
Modified: trunk/GME/Mga/MgaComplexOps.cpp
==============================================================================
--- trunk/GME/Mga/MgaComplexOps.cpp Fri Nov 10 16:01:50 2017 (r2712)
+++ trunk/GME/Mga/MgaComplexOps.cpp Fri Nov 10 16:01:54 2017 (r2713)
@@ -2,6 +2,7 @@
#include "stdafx.h"
#include "MgaFCO.h"
#include <map>
+#include <unordered_set>
#include "MgaComplexOps.h"
#include "MgaSet.h"
#include "limits.h"
@@ -1658,6 +1659,7 @@
MGACOLL_ITERATE(ICoreAttribute, atts) {
attrid_type ai;
CComPtr<ICoreMetaAttribute> mattr;
+
COMTHROW(MGACOLL_ITER->get_MetaAttribute(&mattr));
COMTHROW(mattr->get_AttrID(&ai));
if(ai < ATTRID_COLLECTION) {
@@ -1744,20 +1746,22 @@
switch( ai) {
case ATTRID_ATTRPARENT: // copy the unfilled attributes
{
+#ifdef _DEBUG
unsigned int owned_attrs(0), inherited_attrs(0), l3(0);
CComBSTR nm;
ObjForCore(nobj)->get_Name( &nm);
+#endif
- std::list<metaref_type> ownedAttrVec;
+ std::unordered_set<metaref_type> setAttrs;
{
- CoreObjs my_attrs = nobj[ai + ATTRID_COLLECTION]; // count first the # of owned attributes
+ CoreObjs my_attrs = nobj[ai + ATTRID_COLLECTION];
ITERATE_THROUGH(my_attrs) {
+#ifdef _DEBUG
++owned_attrs;
+#endif
metaref_type attr_i = ITER[ATTRID_META];
- if( std::find( ownedAttrVec.begin(), ownedAttrVec.end(), attr_i) == ownedAttrVec.end())
- ownedAttrVec.push_back( attr_i);
- else
- ASSERT(0); // can an attribute belong to self twice?
+ bool inserted = setAttrs.insert(attr_i).second;
+ ASSERT(inserted); // can an attribute belong to self twice?
}
}
// owned_attrs is the number of owned attributes
@@ -1765,28 +1769,35 @@
// the instance or subtype gets an additional attribute (initially had none)
// thus in case of detaching, we need to distinguish between owned values
// and inherited values (owned preferred)
+ CoreObj baseObject = orig;
+ do {
+ CoreObjs base_attrs = baseObject[ai + ATTRID_COLLECTION]; // copy the base's values selectively
+ ITERATE_THROUGH(base_attrs) {
- {
- CoreObjs base_attrs = orig[ai + ATTRID_COLLECTION]; // copy the base's values selectively
- ITERATE_THROUGH(base_attrs) {
- bool fnd = std::find( ownedAttrVec.begin(), ownedAttrVec.end(), ITER[ATTRID_META]) != ownedAttrVec.end();
- if( !fnd)
+ if (setAttrs.insert(ITER[ATTRID_META]).second == true)
{
+#ifdef _DEBUG
++inherited_attrs;
+#endif
CoreObj nchild;
ObjTreeCopy(mgaproject, ITER, nchild, crealist);
nchild[ai] = nobj;
+ setAttrs.insert(ITER[ATTRID_META]);
}
}
- }
- {
- CoreObjs mine = nobj[ai + ATTRID_COLLECTION]; // overwrite with mine
- ITERATE_THROUGH( mine) {
- ++l3;
- }
- }
+ // folders may not be derived
+ ASSERT(baseObject.IsFCO());
+ } while (baseObject = baseObject[ATTRID_DERIVED]);
+
+#ifdef _DEBUG
+ CoreObjs mine = nobj[ai + ATTRID_COLLECTION];
+ ITERATE_THROUGH(mine) {
+ ++l3;
+ }
ASSERT( owned_attrs + inherited_attrs == l3);
+#endif
+
break;
}
case ATTRID_FCOPARENT: // for all secondary derived fco children-> detach
Modified: trunk/Tests/GPyUnit/test_instances.py
==============================================================================
--- trunk/Tests/GPyUnit/test_instances.py Fri Nov 10 16:01:50 2017 (r2712)
+++ trunk/Tests/GPyUnit/test_instances.py Fri Nov 10 16:01:54 2017 (r2713)
@@ -110,6 +110,23 @@
self.project.CommitTransaction()
@dec_disable_early_binding
+ def test_DetachFromArcheType_Attrs(self):
+ self.project = GPyUnit.util.parse_xme(self.connstr)
+ self.project.BeginTransactionInNewTerr()
+ aspects = self.project.RootFolder.GetObjectByPathDisp("/@Aspects")
+ aspect = self.project.RootFolder.GetObjectByPathDisp("/@Aspects/@Aspect")
+ subtype = self.project.RootFolder.DeriveRootObject(aspects, False)
+ instance = self.project.RootFolder.DeriveRootObject(subtype, True)
+
+ aspect.SetStrAttrByNameDisp("GeneralPreferences", "test123")
+ aspect_instance = instance.GetObjectByPathDisp("/@Aspect")
+ self.assertEquals(aspect.GetStrAttrByNameDisp("GeneralPreferences"), aspect_instance.GetStrAttrByNameDisp("GeneralPreferences"))
+
+ instance.DetachFromArcheType()
+ self.assertEquals(aspect.GetStrAttrByNameDisp("GeneralPreferences"), aspect_instance.GetStrAttrByNameDisp("GeneralPreferences"))
+ self.project.CommitTransaction()
+
+ @dec_disable_early_binding
def test_RemoveArchetypeConnpoint(self):
self.project = GPyUnit.util.parse_xme(self.connstr)
self.project.BeginTransactionInNewTerr()
@@ -190,3 +207,6 @@
self.project.CommitTransaction()
self.project.Save()
+
+if __name__ == "__main__":
+ unittest.main()
More information about the gme-commit
mailing list