Opened 11 years ago

Closed 11 years ago

Last modified 11 years ago

#7515 closed enhancement (invalid)

this.inherited(arguments) exception request

Reported by: ole Owned by: sjmiles
Priority: high Milestone: tbd
Component: Core Version: 1.1.1
Keywords: Cc:
Blocked By: Blocking:

Description

I decided to inherit a method call in child like this:

testMethod: function() {

this.inherited(arguments);

}

In parent I had the same method like this: testMethod: function() {

alert('called from child');

}

However the alert never got triggered. The reason is that a mixin on the child class also had the method:

testMethod: function() {

alert('called from child');

}

When child "Inherits" more than one method from the parent / mixins it does not execute this.inherited(arguments) at all. It would be great if there was an exception saying that:

"testMethod exists on both Parent and ParentMixin? classes. In order for testMethod to be called, in can only exist on one these classes.

Change History (14)

comment:1 Changed 11 years ago by bill

Resolution: invalid
Status: newclosed

You're mixin needs to call this.inherited(arguments) too.

comment:2 Changed 11 years ago by ole

Resolution: invalid
Status: closedreopened

OK - I gave it a shot, as seen below, and it works:

dojo.declare("Parent",

null,

{

testMethod: function() {

alert('Parent.testMethod Called');

}

});

dojo.declare("ParentMixin?",

null,

{

testMethod: function() {

this.inherited(arguments);

}

});

dojo.declare("Child",

[Parent, ParentMixin?],

{

testMethod: function() {

this.inherited(arguments);

}

});

var child = new Child(); child.testMethod();

However I still had to develop tests to find out why this.inherited(arguments) was not getting called the first time around. Is it not possible for dojo inheritance to give further guidance in this case? It seems like it should be possible to detect that the Child instance child has this.inherited(arguments) in it, but one of the mixins does not.

Thoughts?

Thanks,

  • Ole

comment:3 Changed 11 years ago by bill

Well, I don't see how that's possible and I also don't think a mixin necessarily needs to call this.inherited(). Maybe the mixin wants to override the behavior of the subclass, rather than augmenting it (ie, the mixin specifically wants to *not* call the superclass' method).

comment:4 in reply to:  3 Changed 11 years ago by ole

Replying to bill:

Well, I don't see how that's possible and I also don't think a mixin necessarily needs to call this.inherited().

That's exactly what my scenario looks like. My mixin has no reason to call this.inherited. However including the mixin leads to the child not being able to call this.inherited(either), so I had to change the design of the child and parent.

Maybe the mixin wants to override the behavior of the subclass, rather than augmenting it (ie, the mixin specifically wants to *not* call the superclass' method).

Oh OK - I think we are thinking about it from opposite ends. In my case I want the subclass to dominate, and I want it to call the method inherited from the "Main" parent, and just forget about the mixins. However the mixins and "Main" parent all have the same methods, since they all use a "Standard Interface", so nothing gets called.

It would be great to be able to catch this at "Compile Time", such that it did not have to be caught at runtime, since that's a lot cheaper. In the end it only costs someone half an hour / hour to debug, and then if they are like me, they'll submit a ticket...I'd love to be able to eliminate this with minimal cost, which I think means some sort of dojo compiler...the build system could probably contain a rule system that checks for this and generates a report, letting the developer know why the parent method does not get called.

I think this would be a nice marketing feature for dojo, perhaps some of the tooling developers would like to include / support it.

Since dojo is is the most kickass javascript framework ever, I would bet on it.

comment:5 Changed 11 years ago by bill

Oh OK - I think we are thinking about it from opposite ends. In my case I want the subclass to dominate, and I want it to call the method inherited from the "Main" parent, and just forget about the mixins. However the mixins and "Main" parent all have the same methods, since they all use a "Standard Interface", so nothing gets called.

That's not the way dojo.declare() works. Every mixin needs to call this.inherited() (unless you specifically want to block execution up the call chain). This is by design.

It would be great to be able to catch this at "Compile Time", such that it did not have to be

There's nothing to catch, since the computer has no way of knowing what you intended the program to do, and there's no error in the code.

comment:6 in reply to:  5 Changed 11 years ago by ole

There's nothing to catch, since the computer has no way of knowing what you intended the program to do, and there's no error in the code.

Since the computer sees this.inherited(arguments) it knows that the developer intended to call the same method on a parent class right?

comment:7 Changed 11 years ago by ole

One thing that would have really helped me out here is if JSEclipse or whatever editor would have seen that Child was calling this.inherited(arguments) inside the child testMethod. Then examined the parent + mixins and put a flag by the line with some information saying that this.inherited(arguments) will never be called because the method exists on multiple parent classes (The main parent and the mixins).

So if we create a Tooling category for this ticket, and let Aptana, JSEclipse, and other tool developers know that this category is specifically targeted at tooling enhancements then dojo has standard work queue for tooling developers.

So these tickets would not need to be closed, they just exist such that tooling developers can support dojo better.

comment:8 Changed 11 years ago by ole

So maybe we should close this one and reopen another ticket in a tooling category with heading title "Make Editor Flag this.inherited(arguments) When the Parent is Ambiguous"?

comment:9 Changed 11 years ago by sjmiles

Resolution: invalid
Status: reopenedclosed

As you say, it's mostly a matter of perspective, but "dojo.declare" has non-ambiguous parent rule for all superclasses.

Given:

dojo.declare("foo", [bar, zot, nim])

Then the inheritance chain looks like this:

foo -> nim -> zot -> bar

It specifically does not look like this:

foo -> bar

-> zot -> nim

This can be confusing because of the nomenclature. "Mixins" sounds a lot like the latter, but it's really "multiple base classes with limitations". Sometimes I use the phrase "mixin classes" to describe it, but that's not ideal either.

Note also that "mixin classes" can have their own arbitrarily complex hierarchy. So the "inherits" can also walk a tree.

comment:10 Changed 11 years ago by sjmiles

Resolution: invalid
Status: closedreopened

comment:11 Changed 11 years ago by sjmiles

Owner: changed from anonymous to sjmiles
Status: reopenednew

comment:12 Changed 11 years ago by sjmiles

Resolution: invalid
Status: newclosed

comment:13 Changed 11 years ago by sjmiles

My ASCII art didn't come thru so well. Was supposed to look like this:

    foo -> bar
        -> zot 
        -> nim

comment:14 Changed 11 years ago by ole

Ooooooooooh - Dohhh! I see now. One can control which inherited method gets called first by playing with the order of the mixins. Sorry - I thought the call was just being ignored. Thanks for the clarification. I should have caught it on Bill's first comment, but my noodle has limited abilities :-).

Note: See TracTickets for help on using tickets.