Eclipse Community Forums
Forum Search:

Search      Help    Register    Login    Home
Home » Modeling » EMF » Problem with with mutually referencing ELists
Problem with with mutually referencing ELists [message #918158] Thu, 20 September 2012 16:00 Go to next message
Robert Brodt is currently offline Robert Brodt
Messages: 577
Registered: August 2010
Location: Colorado Springs, CO
Senior Member

I ran into an interesting problem today with reference lists. My apologies if this topic has come up before, but I couldn't find anything relevant anywhere...

I have two EClasses "A" and "B" which each contain reference lists to each other, so "A" as a list of references to "B" objects and "B" has a list of references to "A" objects. The lists are both defined as follows:

container=false
containment=false
derived=false
ordered=false
resolve proxies=false
transient=false
unique=true
unsettable=false
upper bound=-1
volatile=false

Given the following XML fragment:

<a id="a_1">
	<bRefs>b_1</bRefs>
</a>
<b id="b_1">
	<aRefs>a_1</aRefs>
</b>


after this fragment is loaded the reference lists each have duplicate entries, which I did not expect! Thus when the document is serialized out again, it becomes this:

<a id="a_1">
	<bRefs>b_1</bRefs>
	<bRefs>b_1</bRefs>
</a>
<b id="b_1">
	<aRefs>a_1</aRefs>
	<aRefs>a_1</aRefs>
</b>


I did verify that the duplicate entries are one and the same object and not two different instances. And, repeating the load/save cycle adds a new entry each time. I also verified that the add() method on these lists works as expected, ignoring duplicates. In other words, the following code:

A a = MyModelFactory.createA();
B b = MyModelFactory.createB();
a.getBRefs().add(b);
a.getBRefs().add(b);
b.getARefs().add(a);
b.getARefs().add(a);


results in only one entry in the a.bRefs list, and one entry in the b.aRefs list!

I've traced this down to XMLHandler.handleForwardReferences() and it looks like this does not obey the list's "uniqueness" attribute and the forward references are always added to the lists.

I've been able to work around this by overriding setValue(EObject,EStructuralFeature,Object,int) in my XMLHelper and checking for duplicate entries in there.

Has anyone run across this before? Is my model definition "incorrect" in the sense that I should be setting some other attributes on these reference lists?

Thanks!
Bob
Re: Problem with with mutually referencing ELists [message #918478 is a reply to message #918158] Thu, 20 September 2012 23:42 Go to previous message
Ed Merks is currently offline Ed Merks
Messages: 25919
Registered: July 2009
Senior Member
<html>
<head>
<meta content="text/html; charset=UTF-8" http-equiv="Content-Type">
</head>
<body bgcolor="#FFFFFF" text="#000000">
Robert,<br>
<br>
There's probably some details you've left out.   In particular, the
serialization you show seems to imply a schema-derived model or at
least one with extended metadata annotations.   XML Scchema
discourages the use of IDREF as the type of an element.  I.e., in
section <a class="moz-txt-link-freetext" href="http://www.w3.org/TR/xmlschema-2/#IDREF">http://www.w3.org/TR/xmlschema-2/#IDREF</a> it states: <br>
<blockquote>For compatibility (see <a
href="http://www.w3.org/TR/xmlschema-2/#terminology">Terminology
(§1.4)</a>) this datatype
should be used only on attributes.
<br>
</blockquote>
But here it's the type of an element (or at least the extended meta
data annotations imply that) and since XML Schema doesn't support
bidirectional references, you're definitely going down a path less
traveled by...<br>
<br>
I suspect that in marked logic below, if IS_MANY_MOVE is true, it
should do a uniqueness test to handle this odd situation:<br>
<br>
      case IS_MANY_ADD:<br>
      case IS_MANY_MOVE:<br>
      {<br>
        @SuppressWarnings("unchecked") InternalEList&lt;Object&gt;
list = (InternalEList&lt;Object&gt;)object.eGet(feature);<br>
<br>
        if (position == -1)<br>
        {<br>
          if (object == value)<br>
          {<br>
            list.add(value);<br>
          }<br>
          else<br>
          {<br>
            list.addUnique(value);  //
&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;&lt;<br>
          }<br>
        }<br>
<br>
Please open a bugzilla with the test case and I'll have a closer
look .<br>
<br>
<br>
<br>
<div class="moz-cite-prefix">On 20/09/2012 10:00 PM, Robert Brodt
wrote:<br>
</div>
<blockquote cite="mid:k3fsk7$7q7$1@xxxxxxxxe.org" type="cite">I
ran into an interesting problem today with reference lists. My
apologies if this topic has come up before, but I couldn't find
anything relevant anywhere...
<br>
<br>
I have two EClasses "A" and "B" which each contain reference lists
to each other, so "A" as a list of references to "B" objects and
"B" has a list of references to "A" objects. The lists are both
defined as follows:
<br>
<br>
container=false
<br>
containment=false
<br>
derived=false
<br>
ordered=false
<br>
resolve proxies=false
<br>
transient=false
<br>
unique=true
<br>
unsettable=false
<br>
upper bound=-1
<br>
volatile=false
<br>
<br>
Given the following XML fragment:
<br>
<br>
<br>
&lt;a id="a_1"&gt;
<br>
    &lt;bRefs&gt;b_1&lt;/bRefs&gt;
<br>
&lt;/a&gt;
<br>
&lt;b id="b_1"&gt;
<br>
    &lt;aRefs&gt;a_1&lt;/aRefs&gt;
<br>
&lt;/b&gt;
<br>
<br>
<br>
after this fragment is loaded the reference lists each have
duplicate entries, which I did not expect! Thus when the document
is serialized out again, it becomes this:
<br>
<br>
<br>
&lt;a id="a_1"&gt;
<br>
    &lt;bRefs&gt;b_1&lt;/bRefs&gt;
<br>
    &lt;bRefs&gt;b_1&lt;/bRefs&gt;
<br>
&lt;/a&gt;
<br>
&lt;b id="b_1"&gt;
<br>
    &lt;aRefs&gt;a_1&lt;/aRefs&gt;
<br>
    &lt;aRefs&gt;a_1&lt;/aRefs&gt;
<br>
&lt;/b&gt;
<br>
<br>
<br>
I did verify that the duplicate entries are one and the same
object and not two different instances. And, repeating the
load/save cycle adds a new entry each time. I also verified that
the add() method on these lists works as expected, ignoring
duplicates. In other words, the following code:
<br>
<br>
<br>
A a = MyModelFactory.createA();
<br>
B b = MyModelFactory.createB();
<br>
a.getBRefs().add(b);
<br>
a.getBRefs().add(b);
<br>
b.getARefs().add(a);
<br>
b.getARefs().add(a);
<br>
<br>
<br>
results in only one entry in the a.bRefs list, and one entry in
the b.aRefs list!
<br>
<br>
I've traced this down to XMLHandler.handleForwardReferences() and
it looks like this does not obey the list's "uniqueness" attribute
and the forward references are always added to the lists.
<br>
<br>
I've been able to work around this by overriding
setValue(EObject,EStructuralFeature,Object,int) in my XMLHelper
and checking for duplicate entries in there.
<br>
<br>
Has anyone run across this before? Is my model definition
"incorrect" in the sense that I should be setting some other
attributes on these reference lists?
<br>
<br>
Thanks!
<br>
Bob
<br>
</blockquote>
<br>
</body>
</html>
Previous Topic:[CDO/Teneo] EMF Specific Extra Columns in DDL
Next Topic:Problem with cross references
Goto Forum:
  


Current Time: Sat Jul 26 15:32:38 EDT 2014

Powered by FUDForum. Page generated in 0.01456 seconds