<!-- 
RSS generated by JIRA (8.20.10#820010-sha1:ace47f9899e9ee25d7157d59aa17ab06aee30d3d) at Wed Feb 07 20:09:49 UTC 2024

It is possible to restrict the fields that are returned in this document by specifying the 'field' parameter in your request.
For example, to request only the issue key and summary append 'field=key&field=summary' to the URL of your request.
-->
<rss version="0.92" >
<channel>
    <title>OpenDaylight JIRA</title>
    <link>https://jira.opendaylight.org</link>
    <description>This file is an XML representation of an issue</description>
    <language>en-us</language>    <build-info>
        <version>8.20.10</version>
        <build-number>820010</build-number>
        <build-date>22-06-2022</build-date>
    </build-info>


<item>
            <title>[MDSAL-440] Reconsider TypeObject equals()/hashCode()</title>
                <link>https://jira.opendaylight.org/browse/MDSAL-440</link>
                <project id="10137" key="MDSAL">mdsal</project>
                    <description>&lt;p&gt;TypeObjects are non-final for the purposes of subtyping, and thus have a non-final hashCode()/equals()/toString() methods.&lt;/p&gt;

&lt;p&gt;As such they are extensible to potentially include other fields and have different equality contracts &#8211; and are using getClass() for their equality contract.&lt;/p&gt;

&lt;p&gt;This seems counter-intuitive in their basic use, where they are being derived &#8211; derived TypeObjects do not override none of these methods. Furthermore toString() method in the first derived object uses strictly its class for identity.&lt;/p&gt;

&lt;p&gt;The combination of these leads to quite surprising behavior:&lt;/p&gt;
&lt;ul&gt;
	&lt;li&gt;equals() between base type and its derived type does not work, but&lt;/li&gt;
	&lt;li&gt;the base type can freely be substituted by the derived type, and&lt;/li&gt;
	&lt;li&gt;when such substitution happens toString() will not identify the object as being of derived type&lt;/li&gt;
&lt;/ul&gt;


&lt;p&gt;From YANG perspective, both are just data, and hence as long as their canonical value matches, they are considered equal &#8211; but then YANG does not really consider substitution as each instantiation defines a particular type, which is to say the set constraints that are acceptable and nothing else.&lt;/p&gt;

&lt;p&gt;I think the intent here was that the first derived type creates a type domain and binds the equality contract in terms of itself and the value it holds &#8211; which would match YANG semantics and reduce surprises &#8211; but in that case we should really define equality in terms of instanceof and make hashCode()/equals()/toString() final.&lt;/p&gt;

&lt;p&gt;&#160;&lt;/p&gt;

&lt;p&gt;An example of a model which is impacted by this change looks roughly like this:&lt;/p&gt;
&lt;div class=&quot;preformatted panel&quot; style=&quot;border-width: 1px;&quot;&gt;&lt;div class=&quot;preformattedContent panelContent&quot;&gt;
&lt;pre&gt;model example {
  typedef base-type {
    type string;
    length 1..5;
  }

  typedef derived-type {
    type base-type;
    length 2..5;
  }
}&lt;/pre&gt;
&lt;/div&gt;&lt;/div&gt;
&lt;p&gt;Under the change proposed by this issue, the two generated objects will compare as equal if they contain &quot;abc&quot;, whereas currently they do not (due to having a different class).&lt;/p&gt;

&lt;p&gt;&#160;&lt;/p&gt;</description>
                <environment></environment>
        <key id="31619">MDSAL-440</key>
            <summary>Reconsider TypeObject equals()/hashCode()</summary>
                <type id="10101" iconUrl="https://jira.opendaylight.org/secure/viewavatar?size=xsmall&amp;avatarId=10318&amp;avatarType=issuetype">Task</type>
                                            <priority id="3" iconUrl="https://jira.opendaylight.org/images/icons/priorities/major.svg">Medium</priority>
                        <status id="5" iconUrl="https://jira.opendaylight.org/images/icons/statuses/resolved.png" description="A resolution has been taken, and it is awaiting verification by reporter. From here issues are either reopened, or are closed.">Resolved</status>
                    <statusCategory id="3" key="done" colorName="green"/>
                                    <resolution id="10000">Done</resolution>
                                        <assignee username="rovarga">Robert Varga</assignee>
                                    <reporter username="rovarga">Robert Varga</reporter>
                        <labels>
                    </labels>
                <created>Fri, 12 Apr 2019 13:29:18 +0000</created>
                <updated>Tue, 7 Jan 2020 13:08:13 +0000</updated>
                            <resolved>Mon, 19 Aug 2019 15:36:29 +0000</resolved>
                                                    <fixVersion>5.0.0</fixVersion>
                                    <component>Binding codegen</component>
                        <due></due>
                            <votes>0</votes>
                                    <watches>1</watches>
                                                                                                                <comments>
                            <comment id="66715" author="rovarga" created="Fri, 12 Apr 2019 13:48:54 +0000"  >&lt;p&gt;&lt;a href=&quot;https://jira.opendaylight.org/browse/YANGTOOLS-418&quot; title=&quot;Deficiencies in current yangtool generation of ietf types.&quot; class=&quot;issue-link&quot; data-issue-key=&quot;YANGTOOLS-418&quot;&gt;YANGTOOLS-418&lt;/a&gt; CanonicalValue works exactly this way: it is a holder of a baseline type, which can be only narrowed-down &#8211; there is one Representation class, which defines the representation and further restrictions are captured by Validated Representation class, which must be a subclass of the Representation class.&lt;/p&gt;

&lt;p&gt;This also works towards &lt;a href=&quot;https://jira.opendaylight.org/browse/MDSAL-90&quot; title=&quot;Simple type derivation relationship lost when binding DTO is translated to DOM and back.&quot; class=&quot;issue-link&quot; data-issue-key=&quot;MDSAL-90&quot;&gt;MDSAL-90&lt;/a&gt;, where the major problem is that if we bounce a TypeObject through DOM, it will lose its original type capture (which is expected), but the real problem is that it will no longer compare as equal &#8211; because it will use a different encapsulation.&lt;/p&gt;

&lt;p&gt;To tie this together:&lt;/p&gt;
&lt;ul&gt;
	&lt;li&gt;&lt;a href=&quot;https://jira.opendaylight.org/browse/YANGTOOLS-418&quot; title=&quot;Deficiencies in current yangtool generation of ietf types.&quot; class=&quot;issue-link&quot; data-issue-key=&quot;YANGTOOLS-418&quot;&gt;YANGTOOLS-418&lt;/a&gt; defines the infrastructure to maintain information about the level of validation while, while forcing coherent equality (through a support class). Assuming proper end-to-end transport and adoption by MD-SAL (so that TypeObjects are CanonicalValues or their holders), this would allow &lt;a href=&quot;https://jira.opendaylight.org/browse/MDSAL-90&quot; title=&quot;Simple type derivation relationship lost when binding DTO is translated to DOM and back.&quot; class=&quot;issue-link&quot; data-issue-key=&quot;MDSAL-90&quot;&gt;MDSAL-90&lt;/a&gt; be solved, i.e. the value would return back with the same class as it originated with, at least until we hit persistence (which would have to maintain complete type information) or externalization (which is happening in &lt;a href=&quot;https://jira.opendaylight.org/browse/MDSAL-90&quot; title=&quot;Simple type derivation relationship lost when binding DTO is translated to DOM and back.&quot; class=&quot;issue-link&quot; data-issue-key=&quot;MDSAL-90&quot;&gt;MDSAL-90&lt;/a&gt;, it&apos;s just that NormalizedNodes are equivalent of persistence without type information).&lt;/li&gt;
	&lt;li&gt;This issue would solve the underlying semantic problem of &lt;a href=&quot;https://jira.opendaylight.org/browse/MDSAL-90&quot; title=&quot;Simple type derivation relationship lost when binding DTO is translated to DOM and back.&quot; class=&quot;issue-link&quot; data-issue-key=&quot;MDSAL-90&quot;&gt;MDSAL-90&lt;/a&gt; by making original and from-DOM objects compare as equal and indinguishable. Note that the derivation can be restored via instanceof checks and fallback instantiation of the derived type &#8211; which is equivalent of CanonicalValueValidator.validateRepresentation() I think. We could perhaps add TypeObject.tryCast() or similar, which would take the top-level derived class, and a Variant describing why the proposed value cannot be validated &#8211; but I am not convinced there are too many uses for it.&lt;/li&gt;
&lt;/ul&gt;


&lt;p&gt;&#160;&lt;/p&gt;

&lt;p&gt;&#160;&lt;/p&gt;</comment>
                            <comment id="66716" author="rovarga" created="Fri, 12 Apr 2019 14:06:34 +0000"  >&lt;p&gt;Another thing that needs to be evaluated is the impact on unions &#8211; I think they are squashing same TypeObjects and getClass() is what makes them work.&lt;/p&gt;</comment>
                            <comment id="66717" author="rovarga" created="Fri, 12 Apr 2019 14:32:17 +0000"  >&lt;p&gt;Some materials around this:&lt;/p&gt;
&lt;ul&gt;
	&lt;li&gt;&lt;a href=&quot;https://www.artima.com/intv/bloch17.html&quot; class=&quot;external-link&quot; target=&quot;_blank&quot; rel=&quot;nofollow noopener&quot;&gt;https://www.artima.com/intv/bloch17.html&lt;/a&gt;&lt;/li&gt;
	&lt;li&gt;&lt;a href=&quot;http://www.angelikalanger.com/Articles/JavaSolutions/SecretsOfEquals/Equals.html&quot; class=&quot;external-link&quot; target=&quot;_blank&quot; rel=&quot;nofollow noopener&quot;&gt;http://www.angelikalanger.com/Articles/JavaSolutions/SecretsOfEquals/Equals.html&lt;/a&gt;&lt;/li&gt;
	&lt;li&gt;&lt;a href=&quot;https://www.artima.com/intv/bloch17.html&quot; class=&quot;external-link&quot; target=&quot;_blank&quot; rel=&quot;nofollow noopener&quot;&gt;https://stackoverflow.com/questions/596462/any-reason-to-prefer-getclass-over-instanceof-when-generating-equals&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;


&lt;p&gt;&#160;&lt;/p&gt;</comment>
                    </comments>
                <issuelinks>
                            <issuelinktype id="10003">
                    <name>Relates</name>
                                            <outwardlinks description="relates to">
                                        <issuelink>
            <issuekey id="22838">YANGTOOLS-418</issuekey>
        </issuelink>
            <issuelink>
            <issuekey id="26912">MDSAL-90</issuekey>
        </issuelink>
                            </outwardlinks>
                                                                <inwardlinks description="relates to">
                                        <issuelink>
            <issuekey id="32293">MDSAL-511</issuekey>
        </issuelink>
                            </inwardlinks>
                                    </issuelinktype>
                    </issuelinks>
                <attachments>
                    </attachments>
                <subtasks>
                    </subtasks>
                <customfields>
                                                                            <customfield id="customfield_11400" key="com.atlassian.jira.plugins.jira-development-integration-plugin:devsummary">
                        <customfieldname>Development</customfieldname>
                        <customfieldvalues>
                            
                        </customfieldvalues>
                    </customfield>
                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                <customfield id="customfield_10000" key="com.pyxis.greenhopper.jira:gh-lexo-rank">
                        <customfieldname>Rank</customfieldname>
                        <customfieldvalues>
                            <customfieldvalue>0|i03nhj:</customfieldvalue>

                        </customfieldvalues>
                    </customfield>
                                                                                                                                                                                                            </customfields>
    </item>
</channel>
</rss>